diff --git a/src/app.tsx b/src/app.tsx
index ee561a73..a469a67a 100644
--- a/src/app.tsx
+++ b/src/app.tsx
@@ -1,8 +1,6 @@
-import { useEffect } from 'react';
import { Outlet, Route, Routes, useLocation, useParams } from 'react-router-dom';
-import { isAllView, isHomeView, isSubscriptionsView } from './lib/utils/view-utils';
+import { isAllView, isHomeView, isNotFoundView, isSubscriptionsView } from './lib/utils/view-utils';
import useIsMobile from './hooks/use-is-mobile';
-import useTheme from './hooks/use-theme';
import styles from './app.module.css';
import Board from './views/board';
import Catalog from './views/catalog';
@@ -16,17 +14,22 @@ import ChallengeModal from './components/challenge-modal';
import PostForm from './components/post-form';
import SubplebbitStats from './components/subplebbit-stats';
import TopBar from './components/topbar';
+import { useEffect } from 'react';
+import { nsfwTags } from './views/home/home';
+import useDefaultSubplebbits from './hooks/use-default-subplebbits';
+import useThemeStore from './stores/use-theme-store';
+import { timeFilterNames } from './hooks/use-time-filter';
const BoardLayout = () => {
- const { accountCommentIndex, subplebbitAddress } = useParams();
+ const { accountCommentIndex, subplebbitAddress, timeFilterName } = useParams();
const location = useLocation();
const isMobile = useIsMobile();
- const isInAllView = isAllView(location.pathname);
- const isInSubscriptionsView = isSubscriptionsView(location.pathname);
+ const isInAllView = isAllView(location.pathname, useParams());
+ const isInSubscriptionsView = isSubscriptionsView(location.pathname, useParams());
const isValidAccountCommentIndex = !accountCommentIndex || (!isNaN(parseInt(accountCommentIndex)) && parseInt(accountCommentIndex) >= 0);
- if (!isValidAccountCommentIndex) {
+ if (!isValidAccountCommentIndex || (timeFilterName && !timeFilterNames.includes(timeFilterName))) {
return ;
}
@@ -56,28 +59,47 @@ const BoardLayout = () => {
);
};
-const App = () => {
+const GlobalLayout = () => {
const location = useLocation();
+ const { subplebbitAddress } = useParams<{ subplebbitAddress: string }>();
+ const getTheme = useThemeStore((state) => state.getTheme);
+ const setTheme = useThemeStore((state) => state.setTheme);
+ const subplebbits = useDefaultSubplebbits();
const isInHomeView = isHomeView(location.pathname);
- const [theme] = useTheme();
+ const isInNotFoundView = isNotFoundView(location.pathname, useParams());
useEffect(() => {
- document.body.classList.forEach((className) => document.body.classList.remove(className));
- const classToAdd = isInHomeView ? 'yotsuba' : theme;
- document.body.classList.add(classToAdd);
- }, [theme, isInHomeView]);
+ let theme = 'yotsuba-b';
- const globalLayout = (
+ if (isInHomeView || isInNotFoundView) {
+ theme = 'yotsuba';
+ } else if (subplebbitAddress) {
+ theme = getTheme(subplebbitAddress);
+ const subplebbit = subplebbits.find((s) => s.address === subplebbitAddress);
+
+ if (subplebbit && subplebbit.tags && subplebbit.tags.some((tag) => nsfwTags.includes(tag)) && theme === 'yotsuba-b') {
+ theme = 'yotsuba';
+ setTheme(subplebbitAddress, 'yotsuba');
+ }
+ }
+
+ document.body.classList.remove('yotsuba', 'yotsuba-b', 'futaba', 'burichan', 'tomorrow', 'photon');
+ document.body.classList.add(theme);
+ }, [location.pathname, subplebbitAddress, getTheme, setTheme, subplebbits, isInHomeView]);
+
+ return (
<>
>
);
+};
+const App = () => {
return (
-
+ }>
} />
}>
} />
diff --git a/src/components/board-buttons/board-buttons.tsx b/src/components/board-buttons/board-buttons.tsx
index 73d9eb2d..3a83ccb9 100644
--- a/src/components/board-buttons/board-buttons.tsx
+++ b/src/components/board-buttons/board-buttons.tsx
@@ -144,11 +144,11 @@ export const TimeFilter = ({ isInAllView, isInCatalogView, isInSubscriptionsView
export const MobileBoardButtons = () => {
const params = useParams();
const location = useLocation();
- const isInAllView = isAllView(location.pathname);
+ const isInAllView = isAllView(location.pathname, params);
const isInCatalogView = isCatalogView(location.pathname, params);
const isInPendingPostPage = isPendingPostView(location.pathname, params);
const isInPostView = isPostPageView(location.pathname, params);
- const isInSubscriptionsView = isSubscriptionsView(location.pathname);
+ const isInSubscriptionsView = isSubscriptionsView(location.pathname, useParams());
const accountComment = useAccountComment({ commentIndex: params?.accountCommentIndex as any });
const subplebbitAddress = params?.subplebbitAddress || accountComment?.subplebbitAddress;
@@ -190,10 +190,10 @@ export const DesktopBoardButtons = () => {
const accountComment = useAccountComment({ commentIndex: params?.accountCommentIndex as any });
const subplebbitAddress = params?.subplebbitAddress || accountComment?.subplebbitAddress;
const isInCatalogView = isCatalogView(location.pathname, params);
- const isInAllView = isAllView(location.pathname);
+ const isInAllView = isAllView(location.pathname, params);
const isInPendingPostPage = isPendingPostView(location.pathname, params);
const isInPostView = isPostPageView(location.pathname, params);
- const isInSubscriptionsView = isSubscriptionsView(location.pathname);
+ const isInSubscriptionsView = isSubscriptionsView(location.pathname, useParams());
return (
<>
diff --git a/src/components/board-header/board-header.tsx b/src/components/board-header/board-header.tsx
index 879a56ba..0227ac26 100644
--- a/src/components/board-header/board-header.tsx
+++ b/src/components/board-header/board-header.tsx
@@ -20,8 +20,8 @@ const BoardHeader = () => {
const location = useLocation();
const params = useParams();
- const isInAllView = isAllView(location.pathname);
- const isInSubscriptionsView = isSubscriptionsView(location.pathname);
+ const isInAllView = isAllView(location.pathname, params);
+ const isInSubscriptionsView = isSubscriptionsView(location.pathname, useParams());
const accountComment = useAccountComment({ commentIndex: params?.accountCommentIndex as any });
const subplebbitAddress = params?.subplebbitAddress || accountComment?.subplebbitAddress;
diff --git a/src/components/catalog-row/catalog-row.tsx b/src/components/catalog-row/catalog-row.tsx
index 4a00693c..5dacf149 100644
--- a/src/components/catalog-row/catalog-row.tsx
+++ b/src/components/catalog-row/catalog-row.tsx
@@ -1,7 +1,7 @@
import { useEffect, useRef, useState } from 'react';
import { createPortal } from 'react-dom';
import { useTranslation } from 'react-i18next';
-import { Link, useLocation } from 'react-router-dom';
+import { Link, useLocation, useParams } from 'react-router-dom';
import { Comment, useComment } from '@plebbit/plebbit-react-hooks';
import { useFloating, offset, shift, size, autoUpdate, Placement } from '@floating-ui/react';
import { getCommentMediaInfo, getHasThumbnail } from '../../lib/utils/media-utils';
@@ -106,7 +106,7 @@ const CatalogPost = ({ post }: { post: Comment }) => {
const { hidden } = useHide({ cid });
const location = useLocation();
- const isInAllView = isAllView(location.pathname);
+ const isInAllView = isAllView(location.pathname, useParams());
const postLink = isInAllView && isDescription ? `/p/all/description` : `/p/${subplebbitAddress}/${isDescription ? 'description' : isRules ? 'rules' : `c/${cid}`}`;
diff --git a/src/components/post-desktop/post-desktop.tsx b/src/components/post-desktop/post-desktop.tsx
index 09b3071e..97c4fcc8 100644
--- a/src/components/post-desktop/post-desktop.tsx
+++ b/src/components/post-desktop/post-desktop.tsx
@@ -34,9 +34,9 @@ const PostInfo = ({ openReplyModal, post, roles, isHidden }: PostProps) => {
const params = useParams();
const location = useLocation();
- const isInAllView = isAllView(location.pathname);
+ const isInAllView = isAllView(location.pathname, params);
const isInPostView = isPostPageView(location.pathname, params);
- const isInSubscriptionsView = isSubscriptionsView(location.pathname);
+ const isInSubscriptionsView = isSubscriptionsView(location.pathname, useParams());
const shortDisplayName = displayName?.trim().length > 20 ? displayName?.trim().slice(0, 20).trim() + '...' : displayName?.trim();
const authorRole = roles?.[address]?.role;
diff --git a/src/components/post-desktop/post-menu-desktop/post-menu-desktop.tsx b/src/components/post-desktop/post-menu-desktop/post-menu-desktop.tsx
index 80313368..e867d882 100644
--- a/src/components/post-desktop/post-menu-desktop/post-menu-desktop.tsx
+++ b/src/components/post-desktop/post-menu-desktop/post-menu-desktop.tsx
@@ -134,10 +134,10 @@ const PostMenuDesktop = ({ post }: { post: Comment }) => {
const location = useLocation();
const params = useParams();
- const isInAllView = isAllView(location.pathname);
+ const isInAllView = isAllView(location.pathname, params);
const isInCatalogView = isCatalogView(location.pathname, params);
const isInPostPageView = isPostPageView(location.pathname, params);
- const isInSubscriptionsView = isSubscriptionsView(location.pathname);
+ const isInSubscriptionsView = isSubscriptionsView(location.pathname, useParams());
const { refs, floatingStyles, context } = useFloating({
placement: 'bottom-start',
diff --git a/src/components/post-form/post-form.tsx b/src/components/post-form/post-form.tsx
index f9718be4..a66cb6f1 100644
--- a/src/components/post-form/post-form.tsx
+++ b/src/components/post-form/post-form.tsx
@@ -77,8 +77,8 @@ const PostFormTable = ({ closeForm }: { closeForm: () => void }) => {
const subjectRef = useRef(null);
const location = useLocation();
- const isInAllView = isAllView(location.pathname);
- const isInSubscriptionsView = isSubscriptionsView(location.pathname);
+ const isInAllView = isAllView(location.pathname, useParams());
+ const isInSubscriptionsView = isSubscriptionsView(location.pathname, useParams());
const subscriptions = account?.subscriptions || [];
const defaultSubplebbitAddresses = useDefaultSubplebbitAddresses();
@@ -262,8 +262,8 @@ const PostForm = () => {
const isInDescriptionView = isDescriptionView(location.pathname, params);
const isInPostView = isPostPageView(location.pathname, params);
const isInRulesView = isRulesView(location.pathname, params);
- const isInAllView = isAllView(location.pathname);
- const isInSubscriptionsView = isSubscriptionsView(location.pathname);
+ const isInAllView = isAllView(location.pathname, params);
+ const isInSubscriptionsView = isSubscriptionsView(location.pathname, useParams());
const comment = useComment({ commentCid: useParams().commentCid });
const { deleted, locked, removed } = comment || {};
diff --git a/src/components/post-mobile/post-mobile.tsx b/src/components/post-mobile/post-mobile.tsx
index fd1d956e..3805e299 100644
--- a/src/components/post-mobile/post-mobile.tsx
+++ b/src/components/post-mobile/post-mobile.tsx
@@ -26,8 +26,8 @@ const PostInfoAndMedia = ({ openReplyModal, post, roles }: PostProps) => {
const { address, displayName, shortAddress } = author || {};
const location = useLocation();
- const isInAllView = isAllView(location.pathname);
- const isInSubscriptionsView = isSubscriptionsView(location.pathname);
+ const isInAllView = isAllView(location.pathname, useParams());
+ const isInSubscriptionsView = isSubscriptionsView(location.pathname, useParams());
const authorRole = roles?.[address]?.role;
const shortDisplayName = displayName?.trim().length > 20 ? displayName?.trim().slice(0, 20).trim() + '...' : displayName?.trim();
@@ -196,7 +196,7 @@ const PostMobile = ({ openReplyModal, post, roles, showAllReplies, showReplies =
const { isDescription, isRules } = post || {}; // custom properties, not from api
const params = useParams();
const location = useLocation();
- const isInAllView = isAllView(location.pathname);
+ const isInAllView = isAllView(location.pathname, params);
const isInPendingPostView = isPendingPostView(location.pathname, params);
const isInPostView = isPostPageView(location.pathname, params);
const linksCount = useCountLinksInReplies(post);
diff --git a/src/components/reply-modal/reply-modal.tsx b/src/components/reply-modal/reply-modal.tsx
index b53a38bc..77a28ced 100644
--- a/src/components/reply-modal/reply-modal.tsx
+++ b/src/components/reply-modal/reply-modal.tsx
@@ -2,7 +2,7 @@ import { useEffect, useRef, useState } from 'react';
import { useLocation, useParams } from 'react-router-dom';
import { useTranslation } from 'react-i18next';
import Draggable from 'react-draggable';
-import { setAccount, useAccount, useSubplebbit } from '@plebbit/plebbit-react-hooks';
+import { setAccount, useAccount, useAuthorAddress, useSubplebbit } from '@plebbit/plebbit-react-hooks';
import Plebbit from '@plebbit/plebbit-js/dist/browser/index.js';
import { getFormattedTimeAgo } from '../../lib/utils/time-utils';
import { isValidURL } from '../../lib/utils/url-utils';
@@ -78,8 +78,8 @@ const ReplyModal = ({ closeModal, parentCid, scrollY }: ReplyModalProps) => {
}, [parentCid]);
const location = useLocation();
- const isInAllView = isAllView(location.pathname);
- const isInSubscriptionsView = isSubscriptionsView(location.pathname);
+ const isInAllView = isAllView(location.pathname, useParams());
+ const isInSubscriptionsView = isSubscriptionsView(location.pathname, useParams());
const subplebbit = useSubplebbit({ subplebbitAddress });
const { updatedAt } = subplebbit || {};
const isBoardOffline = subplebbit?.updatedAt && subplebbit.updatedAt < Date.now() / 1000 - 60 * 60;
diff --git a/src/components/settings-modal/interface-settings/interface-settings.tsx b/src/components/settings-modal/interface-settings/interface-settings.tsx
index 70502659..cf9494eb 100644
--- a/src/components/settings-modal/interface-settings/interface-settings.tsx
+++ b/src/components/settings-modal/interface-settings/interface-settings.tsx
@@ -65,8 +65,12 @@ const CheckForUpdates = () => {
const Style = () => {
const [theme, setTheme] = useTheme();
+ const handleThemeChange = (e: React.ChangeEvent) => {
+ setTheme(e.target.value);
+ };
+
return (
-