Signed-off-by: marcin mikołajczak <git@mkljczk.pl>
environments/review-black-mode-td9fvr/deployments/4468
marcin mikołajczak 2024-03-24 17:38:34 +01:00
rodzic c24fc10c93
commit 067fc9e45d
44 zmienionych plików z 77 dodań i 63 usunięć

Wyświetl plik

@ -293,7 +293,7 @@ const DropdownMenu = (props: IDropdownMenu) => {
data-testid='dropdown-menu'
ref={refs.setFloating}
className={
clsx('z-[1001] w-56 rounded-md bg-white py-1 shadow-lg transition-opacity duration-100 focus:outline-none dark:bg-gray-900 dark:ring-2 dark:ring-primary-700', {
clsx('z-[1001] w-56 rounded-md bg-white py-1 shadow-lg transition-opacity duration-100 focus:outline-none black:bg-black dark:bg-gray-900 dark:ring-2 dark:ring-primary-700', {
'opacity-0 pointer-events-none': !isOpen,
})
}
@ -318,7 +318,7 @@ const DropdownMenu = (props: IDropdownMenu) => {
<div
ref={arrowRef}
style={arrowProps}
className='pointer-events-none absolute z-[-1] h-3 w-3 bg-white dark:bg-gray-900'
className='pointer-events-none absolute z-[-1] h-3 w-3 bg-white black:bg-black dark:bg-gray-900'
/>
</div>
</Portal>

Wyświetl plik

@ -51,7 +51,7 @@ const EventPreview: React.FC<IEventPreview> = ({ status, className, hideAction,
));
return (
<div className={clsx('relative w-full overflow-hidden rounded-lg bg-gray-100 dark:bg-primary-800', className)}>
<div className={clsx('relative w-full overflow-hidden rounded-lg bg-gray-100 black:border black:border-gray-800 black:bg-black dark:bg-primary-800', className)}>
<div className='absolute right-3 top-28'>
{floatingAction && action}
</div>

Wyświetl plik

@ -17,7 +17,7 @@ interface IGroupCard {
const GroupCard: React.FC<IGroupCard> = ({ group }) => {
return (
<Stack
className='relative h-[240px] rounded-lg border border-solid border-gray-300 bg-white dark:border-primary-800 dark:bg-primary-900'
className='relative h-[240px] rounded-lg border border-solid border-gray-300 bg-white black:bg-white dark:border-primary-800 dark:bg-primary-900'
data-testid='group-card'
>
{/* Group Cover Image */}

Wyświetl plik

@ -45,7 +45,7 @@ const GroupPopover = (props: IGroupPopoverContainer) => {
content={
<Stack space={4} className='w-80 pb-4'>
<Stack
className='relative h-60 rounded-lg bg-white dark:border-primary-800 dark:bg-primary-900'
className='relative h-60 rounded-lg bg-white black:bg-white dark:border-primary-800 dark:bg-primary-900'
data-testid='group-card'
>
{/* Group Cover Image */}

Wyświetl plik

@ -2,7 +2,7 @@ import React from 'react';
/** Fullscreen gradient used as a backdrop to public pages. */
const LandingGradient: React.FC = () => (
<div className='fixed h-screen w-full bg-gradient-to-tr from-primary-50 via-white to-gradient-end/10 dark:from-primary-900/50 dark:via-primary-900 dark:to-primary-800/50' />
<div className='fixed h-screen w-full bg-gradient-to-tr from-primary-50 via-white to-gradient-end/10 black:hidden dark:from-primary-900/50 dark:via-primary-900 dark:to-primary-800/50' />
);
export default LandingGradient;

Wyświetl plik

@ -232,7 +232,7 @@ const ModalRoot: React.FC<IModalRoot> = ({ children, onCancel, onClose, type })
<div
role='presentation'
id='modal-overlay'
className='fixed inset-0 bg-gray-500/90 backdrop-blur dark:bg-gray-700/90'
className='fixed inset-0 bg-gray-500/90 backdrop-blur black:bg-gray-900/90 dark:bg-gray-700/90'
onClick={handleOnClose}
/>

Wyświetl plik

@ -144,7 +144,7 @@ const SidebarMenu: React.FC = (): JSX.Element | null => {
}
>
<div
className='fixed inset-0 bg-gray-500/90 dark:bg-gray-700/90'
className='fixed inset-0 bg-gray-500/90 black:bg-gray-900/90 dark:bg-gray-700/90'
role='button'
onClick={handleClose}
/>
@ -153,7 +153,7 @@ const SidebarMenu: React.FC = (): JSX.Element | null => {
<div
className={
clsx({
'flex flex-col flex-1 bg-white dark:bg-primary-900 -translate-x-full rtl:translate-x-full w-full max-w-xs': true,
'flex flex-col flex-1 bg-white black:bg-black dark:bg-primary-900 -translate-x-full rtl:translate-x-full w-full max-w-xs': true,
'!translate-x-0': sidebarOpen,
})
}
@ -350,7 +350,7 @@ const SidebarMenu: React.FC = (): JSX.Element | null => {
</button>
{switcher && (
<div className='border-t-2 border-solid border-gray-100 dark:border-gray-800'>
<div className='border-t-2 border-solid border-gray-100 black:border-t dark:border-gray-800'>
{otherAccounts.map(account => renderAccount(account))}
<NavLink className='flex items-center space-x-1 py-2' to='/login/add' onClick={handleClose}>

Wyświetl plik

@ -49,7 +49,7 @@ const SidebarNavigationLink = React.forwardRef((props: ISidebarNavigationLink, r
count={count}
countMax={countMax}
className={clsx('h-5 w-5', {
'text-gray-600 dark:text-gray-500 group-hover:text-primary-500 dark:group-hover:text-primary-400': !isActive,
'text-gray-600 black:text-white dark:text-gray-500 group-hover:text-primary-500 dark:group-hover:text-primary-400': !isActive,
'text-primary-500 dark:text-primary-400': isActive,
})}
/>

Wyświetl plik

@ -15,7 +15,7 @@ const SiteLogo: React.FC<ISiteLogo> = ({ className, theme, ...rest }) => {
const { logo, logoDarkMode } = useSoapboxConfig();
const { demo } = useSettings();
let darkMode = useTheme() === 'dark';
let darkMode = ['dark', 'black'].includes(useTheme());
if (theme === 'dark') darkMode = true;
/** Soapbox logo. */

Wyświetl plik

@ -232,7 +232,7 @@ const StatusList: React.FC<IStatusList> = ({
placeholderCount={20}
ref={node}
className={clsx('divide-y divide-solid divide-gray-200 dark:divide-gray-800', {
'divide-none': divideType !== 'border',
'divide-none black:divide-solid': divideType !== 'border',
})}
itemClassName={clsx({
'pb-3': divideType !== 'border',

Wyświetl plik

@ -35,7 +35,7 @@ const ThumbNavigationLink: React.FC<IThumbNavigationLink> = ({ count, countMax,
src={src}
className={clsx({
'h-5 w-5': true,
'text-gray-600': !active,
'text-gray-600 black:text-white': !active,
'text-primary-500': active,
})}
count={count}
@ -46,7 +46,7 @@ const ThumbNavigationLink: React.FC<IThumbNavigationLink> = ({ count, countMax,
src={src}
className={clsx({
'h-5 w-5': true,
'text-gray-600': !active,
'text-gray-600 black:text-white': !active,
'text-primary-500': active,
})}
/>

Wyświetl plik

@ -38,9 +38,10 @@ const Card = React.forwardRef<HTMLDivElement, ICard>(({ children, variant = 'def
ref={ref}
{...filteredProps}
className={clsx({
'bg-white dark:bg-primary-900 text-gray-900 dark:text-gray-100 shadow-lg dark:shadow-none': variant === 'rounded',
'bg-white dark:bg-primary-900 black:bg-black text-gray-900 dark:text-gray-100 shadow-lg dark:shadow-none': variant === 'rounded',
[sizes[size]]: variant === 'rounded',
'py-4': variant === 'slim',
'black:rounded-none': size !== 'xl',
}, className)}
>
{children}

Wyświetl plik

@ -102,8 +102,8 @@ const Column: React.FC<IColumn> = React.forwardRef((props, ref: React.ForwardedR
backHref={backHref}
className={clsx({
'rounded-t-3xl': !isScrolled && !transparent,
'sticky top-12 z-10 bg-white/90 dark:bg-primary-900/90 backdrop-blur lg:top-16': !transparent,
'p-4 sm:p-0 sm:pb-4': transparent,
'sticky top-12 z-10 bg-white/90 dark:bg-primary-900/90 black:bg-black/90 backdrop-blur lg:top-16': !transparent,
'p-4 sm:p-0 sm:pb-4 black:p-4': transparent,
'-mt-4 -mx-4 p-4': size !== 'lg' && !transparent,
'-mt-4 -mx-4 p-4 sm:-mt-6 sm:-mx-6 sm:p-6': size === 'lg' && !transparent,
})}

Wyświetl plik

@ -13,7 +13,7 @@ interface IDivider {
const Divider = ({ text, textSize = 'md' }: IDivider) => (
<div className='relative' data-testid='divider'>
<div className='absolute inset-0 flex items-center' aria-hidden='true'>
<div className='w-full border-t-2 border-solid border-gray-100 dark:border-gray-800' />
<div className='w-full border-t-2 border-solid border-gray-100 black:border-t dark:border-gray-800' />
</div>
{text && (

Wyświetl plik

@ -21,7 +21,7 @@ interface LayoutComponent extends React.FC<ILayout> {
/** Layout container, to hold Sidebar, Main, and Aside. */
const Layout: LayoutComponent = ({ children }) => (
<div className='relative sm:pt-4'>
<div className='relative grow black:pt-0 sm:pt-4'>
<div className='mx-auto max-w-3xl sm:px-6 md:grid md:max-w-7xl md:grid-cols-12 md:gap-8 md:px-8'>
{children}
</div>
@ -41,7 +41,7 @@ const Sidebar: React.FC<ISidebar> = ({ children }) => (
const Main: React.FC<React.HTMLAttributes<HTMLDivElement>> = ({ children, className }) => (
<main
className={clsx({
'md:col-span-12 lg:col-span-9 xl:col-span-6 pb-36': true,
'md:col-span-12 lg:col-span-9 xl:col-span-6 pb-36 black:border-gray-800 lg:black:border-l xl:black:border-r': true,
}, className)}
>
{children}

Wyświetl plik

@ -28,7 +28,7 @@ const MenuList: React.FC<IMenuList> = (props) => {
<MenuItems
onKeyDown={(event) => event.nativeEvent.stopImmediatePropagation()}
className={
clsx(className, 'shadow-menu rounded-lg bg-white py-1 dark:bg-primary-900')
clsx(className, 'shadow-menu rounded-lg bg-white py-1 black:bg-black dark:bg-primary-900')
}
{...filteredProps}
/>
@ -37,6 +37,6 @@ const MenuList: React.FC<IMenuList> = (props) => {
};
/** Divides menu items. */
const MenuDivider = () => <hr className='mx-2 my-1 border-t-2 border-gray-100 dark:border-gray-800' />;
const MenuDivider = () => <hr className='mx-2 my-1 border-t-2 border-gray-100 black:border-t dark:border-gray-800' />;
export { Menu, MenuButton, MenuDivider, MenuItems, MenuItem, MenuList, MenuLink };

Wyświetl plik

@ -95,7 +95,7 @@ const Modal = React.forwardRef<HTMLDivElement, IModal>(({
<div
ref={ref}
data-testid='modal'
className={clsx(className, 'pointer-events-auto mx-auto block w-full rounded-2xl bg-white p-6 text-start align-middle text-gray-900 shadow-xl transition-all dark:bg-primary-900 dark:text-gray-100', widths[width])}
className={clsx(className, 'pointer-events-auto mx-auto block w-full rounded-2xl bg-white p-6 text-start align-middle text-gray-900 shadow-xl transition-all black:bg-black dark:bg-primary-900 dark:text-gray-100', widths[width])}
>
<div className='w-full justify-between sm:flex sm:items-start'>
<div className='w-full'>

Wyświetl plik

@ -106,7 +106,7 @@ const Toast = (props: IToast) => {
data-testid='toast'
className={
clsx({
'p-4 pointer-events-auto w-full max-w-sm overflow-hidden rounded-lg bg-white dark:bg-gray-900 shadow-lg dark:ring-2 dark:ring-gray-800': true,
'p-4 pointer-events-auto w-full max-w-sm overflow-hidden rounded-lg bg-white black:bg-black dark:bg-gray-900 shadow-lg dark:ring-2 dark:ring-gray-800': true,
'animate-enter': t.visible,
'animate-leave': !t.visible,
})

Wyświetl plik

@ -110,7 +110,7 @@ const Header: React.FC<IHeader> = ({ account }) => {
return (
<div className='-mx-4 -mt-4 sm:-mx-6 sm:-mt-6'>
<div>
<div className='relative h-32 w-full bg-gray-200 md:rounded-t-xl lg:h-48 dark:bg-gray-900/50' />
<div className='relative h-32 w-full bg-gray-200 black:rounded-t-none md:rounded-t-xl lg:h-48 dark:bg-gray-900/50' />
</div>
<div className='px-4 sm:px-6'>
@ -620,7 +620,7 @@ const Header: React.FC<IHeader> = ({ account }) => {
)}
<div>
<div className='relative isolate flex h-32 w-full flex-col justify-center overflow-hidden bg-gray-200 md:rounded-t-xl lg:h-48 dark:bg-gray-900/50'>
<div className='relative isolate flex h-32 w-full flex-col justify-center overflow-hidden bg-gray-200 black:rounded-t-none md:rounded-t-xl lg:h-48 dark:bg-gray-900/50'>
{renderHeader()}
<div className='absolute left-2 top-2'>

Wyświetl plik

@ -60,15 +60,15 @@ const ChatPage: React.FC<IChatPage> = ({ chatId }) => {
<div
ref={containerRef}
style={{ height }}
className='h-screen overflow-hidden bg-white text-gray-900 shadow-lg sm:rounded-t-xl dark:bg-primary-900 dark:text-gray-100 dark:shadow-none'
className='h-screen overflow-hidden bg-white text-gray-900 shadow-lg black:bg-transparent sm:rounded-t-xl dark:bg-primary-900 dark:text-gray-100 dark:shadow-none'
>
{isOnboarded ? (
<div
className='grid h-full grid-cols-9 overflow-hidden dark:divide-x-2 dark:divide-solid dark:divide-gray-800'
className='grid h-full grid-cols-9 overflow-hidden black:divide-x dark:divide-x-2 dark:divide-solid dark:divide-gray-800'
data-testid='chat-page'
>
<Stack
className={clsx('dark:inset col-span-9 overflow-hidden bg-gradient-to-r from-white to-gray-100 sm:col-span-3 dark:bg-gray-900 dark:bg-none', {
className={clsx('dark:inset col-span-9 overflow-hidden bg-gradient-to-r from-white to-gray-100 black:bg-black sm:col-span-3 dark:bg-gray-900 dark:bg-none', {
'hidden sm:block': isSidebarHidden,
})}
>

Wyświetl plik

@ -12,7 +12,7 @@ interface IPane {
const Pane: React.FC<IPane> = ({ isOpen = false, children }) => {
return (
<div
className={clsx('fixed bottom-0 z-[99] flex w-96 flex-col rounded-t-lg bg-white shadow-3xl ltr:right-5 rtl:left-5 dark:bg-gray-900', {
className={clsx('fixed bottom-0 z-[99] flex w-96 flex-col rounded-t-lg bg-white shadow-3xl black:border black:border-b-0 black:border-gray-800 black:bg-black ltr:right-5 rtl:left-5 dark:bg-gray-900', {
'h-[550px] max-h-[100vh]': isOpen,
'h-16': !isOpen,
})}

Wyświetl plik

@ -80,7 +80,7 @@ const EventHeader: React.FC<IEventHeader> = ({ status }) => {
return (
<>
<div className='-mx-4 -mt-4'>
<div className='relative h-32 w-full bg-gray-200 md:rounded-t-xl lg:h-48 dark:bg-gray-900/50' />
<div className='relative h-32 w-full bg-gray-200 black:rounded-t-none md:rounded-t-xl lg:h-48 dark:bg-gray-900/50' />
</div>
<PlaceholderEventHeader />
@ -363,13 +363,13 @@ const EventHeader: React.FC<IEventHeader> = ({ status }) => {
return (
<>
<div className='-mx-4 -mt-4'>
<div className='relative h-32 w-full bg-gray-200 md:rounded-t-xl lg:h-48 dark:bg-gray-900/50'>
<div className='relative h-32 w-full bg-gray-200 black:rounded-t-none md:rounded-t-xl lg:h-48 dark:bg-gray-900/50'>
{banner && (
<a href={banner.url} onClick={handleHeaderClick} target='_blank'>
<StillImage
src={banner.url}
alt={intl.formatMessage(messages.bannerHeader)}
className='absolute inset-0 h-full object-cover md:rounded-t-xl'
className='absolute inset-0 h-full object-cover black:rounded-t-none md:rounded-t-xl'
/>
</a>
)}

Wyświetl plik

@ -36,7 +36,7 @@ const GroupHeader: React.FC<IGroupHeader> = ({ group }) => {
return (
<div className='-mx-4 -mt-4 sm:-mx-6 sm:-mt-6' data-testid='group-header-missing'>
<div>
<div className='relative h-32 w-full bg-gray-200 md:rounded-t-xl lg:h-48 dark:bg-gray-900/50' />
<div className='relative h-32 w-full bg-gray-200 black:rounded-t-none md:rounded-t-xl lg:h-48 dark:bg-gray-900/50' />
</div>
<div className='px-4 sm:px-6'>

Wyświetl plik

@ -9,7 +9,7 @@ const PlaceholderEventPreview = () => {
const nameLength = randomIntFromInterval(5, 15);
return (
<div className='relative w-full animate-pulse overflow-hidden rounded-lg bg-gray-100 text-primary-50 dark:bg-primary-800 dark:text-primary-800'>
<div className='relative w-full animate-pulse overflow-hidden rounded-lg bg-gray-100 text-primary-50 black:border black:border-gray-800 black:bg-black dark:bg-primary-800 dark:text-primary-800'>
<div className='h-40 bg-primary-200 dark:bg-gray-600' />
<Stack className='p-2.5' space={2}>
<Text weight='semibold'>{generateText(eventNameLength)}</Text>

Wyświetl plik

@ -9,7 +9,7 @@ const PlaceholderGroupCard = () => {
return (
<div className='animate-pulse'>
<Stack className='relative h-[240px] rounded-lg border border-solid border-gray-300 bg-white dark:border-primary-800 dark:bg-primary-900'>
<Stack className='relative h-[240px] rounded-lg border border-solid border-gray-300 bg-white black:bg-white dark:border-primary-800 dark:bg-primary-900'>
{/* Group Cover Image */}
<div className='relative grow basis-1/2 rounded-t-lg bg-gray-300 dark:bg-gray-800' />

Wyświetl plik

@ -8,7 +8,7 @@ import PlaceholderStatusContent from './placeholder-status-content';
/** Fake notification to display while data is loading. */
const PlaceholderNotification = () => (
<div className='bg-white px-4 py-6 sm:p-6 dark:bg-primary-900'>
<div className='bg-white px-4 py-6 black:bg-black sm:p-6 dark:bg-primary-900'>
<div className='w-full animate-pulse'>
<div className='mb-2'>
<PlaceholderStatusContent minLength={20} maxLength={20} />

Wyświetl plik

@ -15,7 +15,7 @@ interface IPlaceholderStatus {
const PlaceholderStatus: React.FC<IPlaceholderStatus> = ({ variant }) => (
<div
className={clsx({
'status-placeholder bg-white dark:bg-primary-900': true,
'status-placeholder bg-white black:bg-black dark:bg-primary-900': true,
'shadow-xl dark:shadow-none sm:rounded-xl px-4 py-6 sm:p-5': variant === 'rounded',
'py-4': variant === 'slim',
})}

Wyświetl plik

@ -57,7 +57,7 @@ const CommunityTimeline = () => {
<Column className='-mt-3 sm:mt-0' label={intl.formatMessage(messages.title)} transparent>
<PinnedHostsPicker />
{showExplanationBox && <div className='mb-4'>
{showExplanationBox && <div className='mb-4 black:mx-4'>
<Accordion
headline={<FormattedMessage id='fediverse_tab.explanation_box.title' defaultMessage='What is the Fediverse?' />}
action={dismissExplanationBox}

Wyświetl plik

@ -22,7 +22,7 @@ const SitePreview: React.FC<ISitePreview> = ({ soapbox }) => {
const userTheme = settings.get('themeMode');
const systemTheme = useSystemTheme();
const dark = userTheme === 'dark' || (userTheme === 'system' && systemTheme === 'dark');
const dark = ['dark', 'black'].includes(userTheme as string) || (userTheme === 'system' && systemTheme === 'dark');
const bodyClass = clsx(
'site-preview',

Wyświetl plik

@ -8,7 +8,7 @@ interface IBackgroundShapes {
/** Gradient that appears in the background of the UI. */
const BackgroundShapes: React.FC<IBackgroundShapes> = ({ position = 'fixed' }) => (
<div className={clsx(position, 'pointer-events-none inset-x-0 top-0 flex justify-center overflow-hidden')}>
<div className={clsx(position, 'pointer-events-none inset-x-0 top-0 flex justify-center overflow-hidden black:hidden')}>
<div className='bg-gradient-sm lg:bg-gradient-light lg:dark:bg-gradient-dark h-screen w-screen' />
</div>
);

Wyświetl plik

@ -70,7 +70,7 @@ const Navbar = () => {
if (mfaToken) return <Redirect to={`/login?token=${encodeURIComponent(mfaToken)}`} />;
return (
<nav className='sticky top-0 z-50 bg-white shadow dark:bg-primary-900' ref={node} data-testid='navbar'>
<nav className='sticky top-0 z-50 bg-white shadow black:border-b black:border-b-gray-800 black:bg-black dark:bg-primary-900' ref={node} data-testid='navbar'>
<div className='mx-auto max-w-7xl px-2 sm:px-6 lg:px-8'>
<div className='relative flex h-12 justify-between lg:h-16'>
{account && (

Wyświetl plik

@ -124,7 +124,7 @@ const ProfileDropdown: React.FC<IProfileDropdown> = ({ account, children }) => {
{visible && (
<div
ref={refs.setFloating}
className='z-[1003] mt-2 max-w-xs rounded-md bg-white shadow-lg focus:outline-none dark:bg-gray-900 dark:ring-2 dark:ring-primary-700'
className='z-[1003] mt-2 max-w-xs rounded-md bg-white shadow-lg focus:outline-none black:bg-black dark:bg-gray-900 dark:ring-2 dark:ring-primary-700'
style={{
position: strategy,
top: y ?? 0,

Wyświetl plik

@ -6,6 +6,7 @@ import { Icon, Select } from 'soapbox/components/ui';
const messages = defineMessages({
light: { id: 'theme_toggle.light', defaultMessage: 'Light' },
dark: { id: 'theme_toggle.dark', defaultMessage: 'Dark' },
black: { id: 'theme_toggle.black', defaultMessage: 'Pure Black' },
system: { id: 'theme_toggle.system', defaultMessage: 'System' },
});
@ -26,6 +27,8 @@ const ThemeSelector: React.FC<IThemeSelector> = ({ value, onChange }) => {
return require('@tabler/icons/sun.svg');
case 'dark':
return require('@tabler/icons/moon.svg');
case 'black':
return require('@tabler/icons/moon-off.svg');
default:
return null;
}
@ -50,6 +53,7 @@ const ThemeSelector: React.FC<IThemeSelector> = ({ value, onChange }) => {
<option value='system'>{intl.formatMessage(messages.system)}</option>
<option value='light'>{intl.formatMessage(messages.light)}</option>
<option value='dark'>{intl.formatMessage(messages.dark)}</option>
<option value='black'>{intl.formatMessage(messages.black)}</option>
</Select>
<div className='pointer-events-none absolute inset-y-0 right-0 flex items-center pr-3'>

Wyświetl plik

@ -480,7 +480,7 @@ const UI: React.FC<IUI> = ({ children }) => {
<BackgroundShapes />
<div className='z-10 flex flex-col'>
<div className='z-10 flex min-h-screen flex-col'>
<Navbar />
<Layout>

Wyświetl plik

@ -1,7 +1,7 @@
import { useSettings } from './useSettings';
import { useSystemTheme } from './useSystemTheme';
type Theme = 'light' | 'dark';
type Theme = 'light' | 'dark' | 'black';
/**
* Returns the actual theme being displayed (eg "light" or "dark")
@ -11,8 +11,7 @@ const useTheme = (): Theme => {
const { themeMode } = useSettings();
const systemTheme = useSystemTheme();
const darkMode = themeMode === 'dark' || (themeMode === 'system' && systemTheme === 'dark');
return darkMode ? 'dark' : 'light';
return themeMode === 'system' ? systemTheme : themeMode;
};
export { useTheme };

Wyświetl plik

@ -22,12 +22,12 @@ const SoapboxHead: React.FC<ISoapboxHead> = ({ children }) => {
const { locale, direction } = useLocale();
const { demo, reduceMotion, underlineLinks, demetricator } = useSettings();
const soapboxConfig = useSoapboxConfig();
const theme = useTheme();
const darkMode = useTheme() === 'dark';
const themeCss = generateThemeCss(demo ? normalizeSoapboxConfig({ brandColor: '#0482d8' }) : soapboxConfig);
const dsn = soapboxConfig.sentryDsn;
const bodyClass = clsx('h-full bg-white text-base dark:bg-gray-800', {
const bodyClass = clsx('h-full bg-white text-base black:bg-black dark:bg-gray-800', {
'no-reduce-motion': !reduceMotion,
'underline-links': underlineLinks,
'demetricator': demetricator,
@ -42,10 +42,10 @@ const SoapboxHead: React.FC<ISoapboxHead> = ({ children }) => {
return (
<>
<Helmet>
<html lang={locale} className={clsx('h-full', { dark: darkMode })} />
<html lang={locale} className={clsx('h-full', { 'dark': theme === 'dark', 'dark black': theme === 'black' })} />
<body className={bodyClass} dir={direction} />
{themeCss && <style id='theme' type='text/css'>{`:root{${themeCss}}`}</style>}
{darkMode && <style type='text/css'>{':root { color-scheme: dark; }'}</style>}
{['dark', 'black'].includes(theme) && <style type='text/css'>{':root { color-scheme: dark; }'}</style>}
<meta name='theme-color' content={soapboxConfig.brandColor} />
</Helmet>

Wyświetl plik

@ -7,7 +7,7 @@ interface IChatsPage {
/** Custom layout for chats on desktop. */
const ChatsPage: React.FC<IChatsPage> = ({ children }) => {
return (
<div className='md:col-span-12 lg:col-span-9'>
<div className='black:border-gray-800 md:col-span-12 lg:col-span-9 lg:black:border-l'>
{children}
</div>
);

Wyświetl plik

@ -50,10 +50,10 @@ const HomePage: React.FC<IHomePage> = ({ children }) => {
return (
<>
<Layout.Main className='space-y-3 pt-3 sm:pt-0 dark:divide-gray-800'>
<Layout.Main className='space-y-3 pt-3 black:space-y-0 sm:pt-0 dark:divide-gray-800'>
{me && (
<Card
className={clsx('relative z-[1] transition', {
className={clsx('relative z-[1] transition black:border-b black:border-gray-800', {
'border-2 border-primary-600 border-dashed z-[99]': isDragging,
'ring-2 ring-offset-2 ring-primary-600': isDraggedOver,
})}

Wyświetl plik

@ -23,7 +23,7 @@ const settingsSchema = z.object({
missingDescriptionModal: z.boolean().catch(false),
defaultPrivacy: z.enum(['public', 'unlisted', 'private', 'direct']).catch('public'),
defaultContentType: z.enum(['text/plain', 'text/markdown']).catch('text/plain'),
themeMode: z.enum(['system', 'light', 'dark']).catch('system'),
themeMode: z.enum(['system', 'light', 'dark', 'black']).catch('system'),
locale: z.string().catch(navigator.language).pipe(z.enum(locales)).catch('en'),
showExplanationBox: z.boolean().catch(true),
explanationBox: z.boolean().catch(true),

Wyświetl plik

@ -1,9 +1,9 @@
.react-datepicker {
@apply dark:bg-gray-900 dark:border-gray-700 p-4 font-sans text-xs text-gray-900 dark:text-gray-300 border border-solid border-gray-200 rounded-lg;
@apply black:bg-black dark:bg-gray-900 dark:border-gray-700 p-4 font-sans text-xs text-gray-900 dark:text-gray-300 border border-solid border-gray-200 rounded-lg;
}
.react-datepicker__input-container > input {
@apply dark:bg-gray-900 dark:text-gray-100 block w-full sm:text-sm border-gray-400 dark:border-gray-800 rounded-md focus:ring-primary-500 focus:border-primary-500;
@apply black:bg-black dark:bg-gray-900 dark:text-gray-100 block w-full sm:text-sm border-gray-400 dark:border-gray-800 rounded-md focus:ring-primary-500 focus:border-primary-500;
&.has-error {
@apply text-red-600 border-red-600;
@ -24,7 +24,7 @@
}
.react-datepicker__header {
@apply bg-white dark:bg-gray-900 border-b-0 py-1 px-0;
@apply bg-white black:bg-black dark:bg-gray-900 border-b-0 py-1 px-0;
}
.react-datepicker__current-month,
@ -85,11 +85,13 @@
}
.react-datepicker__time {
@apply dark:bg-gray-900;
&-container & {
@apply dark:bg-gray-900 black:bg-black;
}
}
.react-datepicker__time-container {
@apply dark:border-gray-700;
@apply dark:border-gray-700 black:border-gray-800;
}
.react-datepicker__day-name,

Wyświetl plik

@ -1,5 +1,5 @@
.thread {
@apply bg-white dark:bg-primary-900;
@apply bg-white black:bg-black dark:bg-primary-900;
&__status {
@apply relative pb-4;

Wyświetl plik

@ -8,3 +8,7 @@ em-emoji-picker {
.dark em-emoji-picker {
--rgb-background: var(--color-primary-900);
}
.black em-emoji-picker {
--rgb-background: var(--color-gray-900);
}

Wyświetl plik

@ -1,5 +1,5 @@
.thumb-navigation {
@apply fixed lg:hidden bottom-0 bg-white/90 dark:bg-primary-900/90 backdrop-blur-md border-t border-solid border-gray-200 dark:border-gray-800 left-0 right-0 shadow-2xl w-full flex z-50;
@apply fixed lg:hidden bottom-0 bg-white/90 black:bg-black/90 dark:bg-primary-900/90 backdrop-blur-md border-t border-solid border-gray-200 dark:border-gray-800 left-0 right-0 shadow-2xl w-full flex z-50;
padding-bottom: env(safe-area-inset-bottom); /* iOS PWA */
overflow-x: auto;
scrollbar-width: thin;

Wyświetl plik

@ -2,9 +2,12 @@ import aspectRatioPlugin from '@tailwindcss/aspect-ratio';
import formsPlugin from '@tailwindcss/forms';
import typographyPlugin from '@tailwindcss/typography';
import { type Config } from 'tailwindcss';
import plugin from 'tailwindcss/plugin';
import { parseColorMatrix } from './tailwind/colors';
const blackVariantPlugin = plugin(({ addVariant }) => addVariant('black', '.black &'));
const config: Config = {
content: ['./src/**/*.{html,js,ts,tsx}', './custom/instance/**/*.html', './index.html'],
darkMode: 'class',
@ -105,6 +108,7 @@ const config: Config = {
aspectRatioPlugin,
formsPlugin,
typographyPlugin,
blackVariantPlugin,
],
};