mirror of
https://github.com/aljazceru/landscape-template.git
synced 2025-12-30 20:44:21 +01:00
change: change search component
- changed search component structure & api due to it being displayed differently in mobile & desktop
This commit is contained in:
@@ -1,48 +1,30 @@
|
||||
|
||||
import { BsSearch } from "react-icons/bs";
|
||||
import { motion } from "framer-motion";
|
||||
import { useAppDispatch, useAppSelector, useCurrentSection } from "src/utils/hooks";
|
||||
import { openModal } from "src/redux/features/modals.slice";
|
||||
import Button from "../Button/Button";
|
||||
import { useAppSelector, useCurrentSection } from "src/utils/hooks";
|
||||
import ASSETS from "src/assets";
|
||||
import Search from "./Search/Search";
|
||||
import IconButton from "../IconButton/IconButton";
|
||||
import { toggleSearch } from "src/redux/features/ui.slice";
|
||||
import { navLinks } from "./Navbar";
|
||||
import { Link, useNavigate } from "react-router-dom";
|
||||
import CategoriesList from "./CategoriesList/CategoriesList";
|
||||
import { useEffect, useRef, useState } from "react";
|
||||
import { IoExtensionPuzzle } from "react-icons/io5";
|
||||
import { useClickOutside, useToggle } from "@react-hookz/web";
|
||||
import { useState } from "react";
|
||||
import {
|
||||
Menu,
|
||||
MenuItem,
|
||||
MenuButton,
|
||||
MenuDivider,
|
||||
SubMenu
|
||||
} from '@szhsin/react-menu';
|
||||
import '@szhsin/react-menu/dist/index.css';
|
||||
import { FiAward, FiChevronDown, FiFeather, FiMic, FiSend } from "react-icons/fi";
|
||||
import { MdComment, MdOutlineExplore, MdOutlineLocalFireDepartment } from "react-icons/md";
|
||||
import { IoMdTrophy } from "react-icons/io";
|
||||
import { BiCoinStack } from "react-icons/bi";
|
||||
import { FiAward, FiChevronDown, FiFeather, FiMic } from "react-icons/fi";
|
||||
|
||||
|
||||
export default function NavDesktop() {
|
||||
const dispatch = useAppDispatch();
|
||||
const [categoriesOpen, toggleCategories] = useToggle(false)
|
||||
const categoriesRef = useRef<HTMLLIElement>(null)
|
||||
useClickOutside(categoriesRef, () => toggleCategories(false))
|
||||
const [searchOpen, setSearchOpen] = useState(false)
|
||||
|
||||
|
||||
const { isWalletConnected, searchOpen } = useAppSelector((state) => ({
|
||||
const { isWalletConnected } = useAppSelector((state) => ({
|
||||
isWalletConnected: state.wallet.isConnected,
|
||||
searchOpen: state.ui.isSearchOpen
|
||||
}));
|
||||
|
||||
|
||||
const handleSearchClick = () => {
|
||||
dispatch(toggleSearch())
|
||||
const openSearch = () => {
|
||||
setSearchOpen(true);
|
||||
};
|
||||
|
||||
|
||||
@@ -50,7 +32,7 @@ export default function NavDesktop() {
|
||||
const navigate = useNavigate()
|
||||
|
||||
|
||||
return (<nav className="bg-white w-full flex fixed h-[72px] top-0 left-0 py-36 px-32 items-center z-[2010]">
|
||||
return (<nav className="bg-white w-full flex fixed top-0 left-0 py-16 px-32 items-center z-[2010]">
|
||||
<a href="https://bolt.fun/">
|
||||
<h2 className="text-h5 font-bold mr-40 lg:mr-64">
|
||||
<img className='h-40' src={ASSETS.Logo} alt="Bolt fun logo" />
|
||||
@@ -159,12 +141,39 @@ export default function NavDesktop() {
|
||||
: <Button className="ml-16 py-12 px-16 lg:px-20" onClick={onConnectWallet}><AiFillThunderbolt className='inline-block text-thunder transform scale-125' /> Connect Wallet </Button>
|
||||
} */}
|
||||
|
||||
{currentSection === 'products' && <IconButton className='ml-16 self-center' onClick={handleSearchClick}>
|
||||
{currentSection === 'products' && <IconButton className='ml-16 self-center' onClick={openSearch}>
|
||||
<BsSearch className='scale-125 text-gray-400' />
|
||||
</IconButton>}
|
||||
</motion.div>
|
||||
<Search />
|
||||
|
||||
<div className="relative h-24">
|
||||
<motion.div
|
||||
initial={{
|
||||
opacity: 0,
|
||||
x: '100%'
|
||||
}}
|
||||
animate={searchOpen ? {
|
||||
opacity: 1,
|
||||
x: '0',
|
||||
transition: { type: "spring", stiffness: 70 }
|
||||
|
||||
} : {
|
||||
opacity: 0,
|
||||
x: '100%',
|
||||
transition: {
|
||||
ease: "easeIn"
|
||||
}
|
||||
}}
|
||||
className='absolute top-0 right-0 flex items-center h-full'
|
||||
>
|
||||
<Search
|
||||
width={326}
|
||||
isOpen={searchOpen}
|
||||
onClose={() => setSearchOpen(false)}
|
||||
onResultClick={() => setSearchOpen(false)}
|
||||
/>
|
||||
</motion.div>
|
||||
</div>
|
||||
</nav>
|
||||
);
|
||||
}
|
||||
|
||||
@@ -1,22 +1,18 @@
|
||||
import { motion } from "framer-motion";
|
||||
import { useEffect, useRef, useState } from "react";
|
||||
import { BsChevronDown, BsSearch } from "react-icons/bs";
|
||||
import { useEffect } from "react";
|
||||
import { BsChevronDown } from "react-icons/bs";
|
||||
import { GrClose } from "react-icons/gr";
|
||||
import Button from "../Button/Button";
|
||||
import ASSETS from "src/assets";
|
||||
import Search from "./Search/Search";
|
||||
import IconButton from "../IconButton/IconButton";
|
||||
import { useAppDispatch, useAppSelector } from "src/utils/hooks";
|
||||
import { toggleSearch } from "src/redux/features/ui.slice";
|
||||
import { FiAward, FiChevronDown, FiFeather, FiMenu, FiMic, } from "react-icons/fi";
|
||||
import { Link, useNavigate } from "react-router-dom";
|
||||
import { useAppSelector } from "src/utils/hooks";
|
||||
import { FiAward, FiFeather, FiMenu, FiMic, } from "react-icons/fi";
|
||||
import { Link } from "react-router-dom";
|
||||
import { useToggle } from "@react-hookz/web";
|
||||
import styles from './styles.module.css'
|
||||
import { Menu, MenuButton, MenuItem, } from "@szhsin/react-menu";
|
||||
import '@szhsin/react-menu/dist/index.css';
|
||||
|
||||
interface Props {
|
||||
}
|
||||
|
||||
|
||||
const navBtnVariant = {
|
||||
@@ -55,19 +51,13 @@ const listArrowVariants = {
|
||||
}
|
||||
|
||||
|
||||
export default function NavMobile({ }: Props) {
|
||||
const dispatch = useAppDispatch();
|
||||
const { searchOpen } = useAppSelector((state) => ({
|
||||
isWalletConnected: state.wallet.isConnected,
|
||||
searchOpen: state.ui.isSearchOpen
|
||||
}));
|
||||
export default function NavMobile() {
|
||||
|
||||
|
||||
const [drawerOpen, toggleDrawerOpen] = useToggle(false);
|
||||
const [communityOpen, toggleCommunityOpen] = useToggle(false)
|
||||
|
||||
|
||||
|
||||
|
||||
useEffect(() => {
|
||||
if (drawerOpen) document.body.style.overflowY = "hidden";
|
||||
else document.body.style.overflowY = "initial";
|
||||
@@ -75,39 +65,19 @@ export default function NavMobile({ }: Props) {
|
||||
|
||||
|
||||
|
||||
const handleSearchClick = () => {
|
||||
toggleDrawerOpen(false)
|
||||
dispatch(toggleSearch())
|
||||
};
|
||||
|
||||
|
||||
|
||||
|
||||
return (
|
||||
<div className={`${styles.navMobile} w-screen z-[2010]`}>
|
||||
<nav className={`bg-white fixed top-0 left-0 h-[67px] w-full p-16 px-32 flex justify-between items-center z-[2010]`}>
|
||||
{/* <div className="w-40 h-40 bg-gray-100 rounded-8 mr-auto">
|
||||
<img className="w-full h-full object-cover" src="https://www.figma.com/file/OFowr5RJk9YZCW35KT7D5K/image/07b85d84145942255afd215b3da26dbbf1dd03bd?fuid=772401335362859303" alt="" />
|
||||
</div> */}
|
||||
<a href="https://bolt.fun/">
|
||||
<img className='h-32' src={ASSETS.Logo} alt="Bolt fun logo" />
|
||||
</a>
|
||||
|
||||
<div className="ml-auto"></div>
|
||||
<motion.div
|
||||
animate={searchOpen ? { opacity: 0 } : { opacity: 1 }}
|
||||
className="flex"
|
||||
>
|
||||
{/* <IconButton className='ml-8 self-center' onClick={handleSearchClick}>
|
||||
<BsSearch className="text-gray-400" />
|
||||
</IconButton> */}
|
||||
<IconButton className='auto text-2xl w-[50px] h-[50px] hover:bg-gray-200 self-center' onClick={() => toggleDrawerOpen()}>
|
||||
{!drawerOpen ? (<motion.div key={drawerOpen ? 1 : 0} variants={navBtnVariant} initial='menuHide' animate='menuShow'><FiMenu /></motion.div>)
|
||||
: (<motion.div key={drawerOpen ? 1 : 0} variants={navBtnVariant} initial='closeHide' animate='closeShow'><GrClose /></motion.div>)}
|
||||
</IconButton>
|
||||
</motion.div>
|
||||
<Search width='calc(100vw - 64px)' />
|
||||
|
||||
<IconButton className='auto text-2xl w-[50px] h-[50px] hover:bg-gray-200 self-center' onClick={() => toggleDrawerOpen()}>
|
||||
{!drawerOpen ? (<motion.div key={drawerOpen ? 1 : 0} variants={navBtnVariant} initial='menuHide' animate='menuShow'><FiMenu /></motion.div>)
|
||||
: (<motion.div key={drawerOpen ? 1 : 0} variants={navBtnVariant} initial='closeHide' animate='closeShow'><GrClose /></motion.div>)}
|
||||
</IconButton>
|
||||
</nav>
|
||||
|
||||
<div className="fixed left-0 pointer-events-none z-[2010] w-full min-h-[calc(100vh-76px)]">
|
||||
@@ -124,6 +94,7 @@ export default function NavMobile({ }: Props) {
|
||||
animate={drawerOpen ? "show" : "hide"}
|
||||
>
|
||||
<div className="flex flex-col gap-16 py-16">
|
||||
<Search onResultClick={() => toggleDrawerOpen(false)} />
|
||||
<a
|
||||
href="https://airtable.com/shr2VkxarNsIFilDz"
|
||||
target="_blank"
|
||||
@@ -132,28 +103,14 @@ export default function NavMobile({ }: Props) {
|
||||
<Button
|
||||
color="primary"
|
||||
fullWidth
|
||||
className="py-12 px-40 rounded-24 "
|
||||
className="!py-16 px-40 rounded-12 "
|
||||
>
|
||||
Submit LApp️
|
||||
Get your product listed
|
||||
</Button>
|
||||
</a>
|
||||
|
||||
<Button
|
||||
color='white'
|
||||
fullWidth
|
||||
className="py-12 px-40 rounded-24"
|
||||
onClick={() => handleSearchClick()}
|
||||
|
||||
>
|
||||
<BsSearch className='inline-block transform scale-125' />
|
||||
<span className="align-middle"> Search Apps</span>
|
||||
</Button>
|
||||
{/* <Button color='gray' fullWidth className="py-12 px-40 rounded-24 my-16"> <AiFillThunderbolt className='inline-block text-thunder transform scale-125' /> Connect Wallet </Button> */}
|
||||
</div>
|
||||
<ul className="px-32 flex flex-col py-16 gap-32 border-t">
|
||||
{/* {navLinks.map((link, idx) => <li key={idx} className="text-body3 p-16 active:bg-gray-200">
|
||||
<Link to={link.url} onClick={() => toggleDrawerOpen(false)}><link.icon className={`text-body2 inline-block mr-12 text-primary-600`} /> <span className="align-middle">{link.text}</span> </Link></li>
|
||||
)} */}
|
||||
|
||||
<li className="relative">
|
||||
<Link
|
||||
to={'/products'}
|
||||
@@ -198,7 +155,7 @@ export default function NavMobile({ }: Props) {
|
||||
</p>
|
||||
</div>
|
||||
</Link>
|
||||
<p
|
||||
<div
|
||||
|
||||
className='font-medium flex gap-16 !rounded-12 opacity-60'
|
||||
>
|
||||
@@ -213,7 +170,7 @@ export default function NavMobile({ }: Props) {
|
||||
Coming soon
|
||||
</p>
|
||||
</div>
|
||||
</p>
|
||||
</div>
|
||||
<Link
|
||||
to="/hackathons"
|
||||
onClick={() => toggleDrawerOpen(false)}
|
||||
|
||||
@@ -1,15 +1,16 @@
|
||||
import React, { FormEvent, useEffect, useRef, useState } from 'react'
|
||||
import React, { FormEvent, useRef, useState } from 'react'
|
||||
import { motion } from 'framer-motion'
|
||||
import { BsSearch } from 'react-icons/bs';
|
||||
import { useClickOutside, useThrottledCallback } from '@react-hookz/web'
|
||||
import { useClickOutside, useThrottledCallback, useUpdateEffect } from '@react-hookz/web'
|
||||
import SearchResults from './SearchResults/SearchResults'
|
||||
import { useAppDispatch, useAppSelector } from 'src/utils/hooks';
|
||||
import { toggleSearch } from 'src/redux/features/ui.slice';
|
||||
import { SearchProjectsQuery, useSearchProjectsLazyQuery } from 'src/graphql';
|
||||
|
||||
interface Props {
|
||||
height?: number | string;
|
||||
width?: number | string;
|
||||
onClose?: () => void;
|
||||
onResultClick?: () => void;
|
||||
isOpen?: boolean;
|
||||
}
|
||||
|
||||
export type ProjectSearchItem = SearchProjectsQuery['searchProjects'][number];
|
||||
@@ -27,24 +28,26 @@ const SearchResultsListVariants = {
|
||||
}
|
||||
}
|
||||
|
||||
export default function Search({
|
||||
|
||||
export default function Search({
|
||||
width,
|
||||
height,
|
||||
onClose,
|
||||
onResultClick,
|
||||
isOpen
|
||||
}: Props) {
|
||||
|
||||
const inputRef = useRef<HTMLInputElement>(null);
|
||||
const [searchInput, setSearchInput] = useState("");
|
||||
const containerRef = useRef<HTMLDivElement>(null)
|
||||
|
||||
const { isOpen } = useAppSelector(state => ({
|
||||
isOpen: state.ui.isSearchOpen
|
||||
}))
|
||||
const dispatch = useAppDispatch()
|
||||
// const { isOpen } = useAppSelector(state => ({
|
||||
// isOpen: state.ui.isSearchOpen
|
||||
// }))
|
||||
// const dispatch = useAppDispatch()
|
||||
|
||||
useClickOutside(containerRef, () => {
|
||||
if (isOpen)
|
||||
dispatch(toggleSearch(false))
|
||||
onClose?.()
|
||||
})
|
||||
|
||||
|
||||
@@ -72,7 +75,7 @@ export default function Search({
|
||||
// onSearch(searchInput);
|
||||
};
|
||||
|
||||
useEffect(() => {
|
||||
useUpdateEffect(() => {
|
||||
if (isOpen)
|
||||
inputRef.current?.focus();
|
||||
else {
|
||||
@@ -83,43 +86,27 @@ export default function Search({
|
||||
|
||||
|
||||
return (
|
||||
<div className="relative h-full" ref={containerRef}>
|
||||
|
||||
{<motion.form
|
||||
initial={{
|
||||
opacity: 0,
|
||||
x: '100%'
|
||||
}}
|
||||
animate={isOpen ? {
|
||||
opacity: 1,
|
||||
x: '0',
|
||||
transition: { type: "spring", stiffness: 70 }
|
||||
|
||||
} : {
|
||||
opacity: 0,
|
||||
x: '100%',
|
||||
transition: {
|
||||
ease: "easeIn"
|
||||
}
|
||||
}}
|
||||
className='absolute top-0 right-0 flex items-center h-full'
|
||||
<div className="relative z-20 h-full" ref={containerRef}>
|
||||
{<form
|
||||
className='flex items-center h-full'
|
||||
onSubmit={handleSubmit}
|
||||
style={{
|
||||
width: width ?? '326px',
|
||||
width: width ?? '100%',
|
||||
height: height ?? '100%'
|
||||
}}
|
||||
>
|
||||
<div className="input-wrapper bg-white !rounded-12 ring-1 ring-gray-400">
|
||||
<BsSearch className={`input-icon`} />
|
||||
<div className="input-wrapper border-0 !p-16 md:!py-12 !bg-gray-100 focus-within:!bg-gray-50 focus:ring-1 focus:ring-gray-300 !rounded-12">
|
||||
<BsSearch className={`input-icon w-16 mr-10 !p-0`} />
|
||||
<input
|
||||
autoFocus
|
||||
type='text'
|
||||
ref={inputRef}
|
||||
className="input-text placeholder-black pl-0"
|
||||
className="input-text placeholder-black !p-0"
|
||||
placeholder='Search'
|
||||
value={searchInput}
|
||||
onChange={handleChange}
|
||||
onKeyDown={e => {
|
||||
if (e.key === 'Escape') dispatch(toggleSearch(false))
|
||||
if (e.key === 'Escape') onClose?.()
|
||||
|
||||
}}
|
||||
/>
|
||||
@@ -134,9 +121,10 @@ export default function Search({
|
||||
<SearchResults
|
||||
isLoading={loading}
|
||||
projects={data?.searchProjects}
|
||||
onResultClick={onResultClick}
|
||||
/>
|
||||
</motion.div>
|
||||
</motion.form>}
|
||||
</form>}
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
|
||||
import { openModal } from 'src/redux/features/modals.slice';
|
||||
import { openProject } from 'src/redux/features/project.slice';
|
||||
import { toggleSearch } from 'src/redux/features/ui.slice';
|
||||
import { useAppDispatch } from 'src/utils/hooks';
|
||||
import { ProjectSearchItem } from '../Search';
|
||||
import SearchProjectCard from '../SearchProjectCard/SearchProjectCard';
|
||||
@@ -10,14 +9,15 @@ import styles from './styles.module.css'
|
||||
interface Props {
|
||||
isLoading?: boolean;
|
||||
projects: ProjectSearchItem[] | undefined,
|
||||
onResultClick?: () => void
|
||||
}
|
||||
|
||||
export default function SearchResults({ projects, isLoading }: Props) {
|
||||
export default function SearchResults({ projects, isLoading, onResultClick }: Props) {
|
||||
|
||||
const dispatch = useAppDispatch();
|
||||
|
||||
const handleOpenProject = (projectId: number) => {
|
||||
dispatch(toggleSearch(false))
|
||||
onResultClick?.()
|
||||
dispatch(openModal({ Modal: "ProjectDetailsCard", props: { projectId } }))
|
||||
}
|
||||
|
||||
|
||||
@@ -37,9 +37,9 @@ export default function HackathonsPage() {
|
||||
<SortByFilter
|
||||
filterChanged={setSortByFilter}
|
||||
/>
|
||||
<TopicsFilter
|
||||
{/* <TopicsFilter
|
||||
filterChanged={setTopicsFilter}
|
||||
/>
|
||||
/> */}
|
||||
<Button
|
||||
href='https://airtable.com/some-registration-form'
|
||||
newTab
|
||||
|
||||
@@ -30,7 +30,7 @@ export default function BountyCard({ bounty }: Props) {
|
||||
}
|
||||
|
||||
return (
|
||||
<div className="bg-white rounded-12 overflow-hidden border">
|
||||
<div className="bg-white rounded-12 overflow-hidden border-2">
|
||||
<img src={bounty.cover_image} className='h-[200px] w-full object-cover bg-gray-100' alt="" />
|
||||
<div className="p-24">
|
||||
<Header author={bounty.author} date={bounty.createdAt} />
|
||||
|
||||
@@ -30,7 +30,7 @@ interface Props {
|
||||
}
|
||||
export default function QuestionCard({ question }: Props) {
|
||||
return (
|
||||
<div className="bg-white rounded-12 overflow-hidden border">
|
||||
<div className="bg-white rounded-12 overflow-hidden border-2">
|
||||
{/* <img src={question.cover_image} className='h-[200px] w-full object-cover' alt="" /> */}
|
||||
<div className="p-24">
|
||||
<Header author={question.author} date={question.createdAt} />
|
||||
|
||||
@@ -29,7 +29,7 @@ export default function StoryCard({ story }: Props) {
|
||||
});
|
||||
|
||||
return (
|
||||
<div className="bg-white rounded-12 overflow-hidden border">
|
||||
<div className="bg-white rounded-12 overflow-hidden border-2">
|
||||
<img src={story.cover_image} className='h-[200px] w-full object-cover' alt="" />
|
||||
<div className="p-24">
|
||||
<Header author={story.author} date={story.createdAt} />
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
import { MdLocalFireDepartment } from "react-icons/md";
|
||||
import { numberFormatter } from "src/utils/helperFunctions";
|
||||
import { ProjectCard } from "src/utils/interfaces";
|
||||
|
||||
|
||||
@@ -20,7 +21,7 @@ export default function ProjectCardMini({ project, onClick }: Props) {
|
||||
<div className="justify-around items-start min-w-0">
|
||||
<p className="text-body4 w-full font-bold overflow-ellipsis overflow-hidden whitespace-nowrap">{project.title}</p>
|
||||
<p className="text-body5 text-gray-600 font-light my-[5px]">{project.category.title}</p>
|
||||
<span className="chip-small bg-warning-50 text-yellow-700 font-light text-body5 py-[3px] px-10"> <MdLocalFireDepartment className='inline-block text-fire transform text-body4 align-middle' /> {project.votes_count} </span>
|
||||
<span className="chip-small bg-warning-50 text-yellow-700 font-light text-body5 py-[3px] px-10"> <MdLocalFireDepartment className='inline-block text-fire transform text-body4 align-middle' /> {numberFormatter(project.votes_count)} </span>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
|
||||
@@ -15,6 +15,7 @@ import Lightbox from 'src/Components/Lightbox/Lightbox'
|
||||
import linkifyHtml from 'linkify-html';
|
||||
import ErrorMessage from 'src/Components/ErrorMessage/ErrorMessage';
|
||||
import { setVoteAmount } from 'src/redux/features/vote.slice';
|
||||
import { numberFormatter } from 'src/utils/helperFunctions';
|
||||
|
||||
|
||||
interface Props extends ModalCard {
|
||||
@@ -114,7 +115,7 @@ export default function ProjectDetailsCard({ direction, projectId, ...props }: P
|
||||
<div>
|
||||
<span className="chip-small font-light text-body5 py-4 px-12 mr-8"> {project?.category.title}</span>
|
||||
|
||||
<span className="chip-small bg-warning-50 font-light text-body5 py-4 px-12"><MdLocalFireDepartment className='inline-block text-fire transform text-body4 align-middle' /> {project?.votes_count}</span>
|
||||
<span className="chip-small bg-warning-50 font-light text-body5 py-4 px-12"><MdLocalFireDepartment className='inline-block text-fire transform text-body4 align-middle' /> {numberFormatter(project?.votes_count)}</span>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@@ -3,13 +3,11 @@ import { createSlice, PayloadAction } from "@reduxjs/toolkit";
|
||||
interface StoreState {
|
||||
navHeight: number;
|
||||
isMobileScreen: boolean;
|
||||
isSearchOpen: boolean
|
||||
}
|
||||
|
||||
const initialState = {
|
||||
navHeight: 0,
|
||||
isMobileScreen: /Android|webOS|iPhone|iPad|iPod|BlackBerry/i.test(navigator.userAgent) || window.innerWidth < 480,
|
||||
isSearchOpen: false,
|
||||
} as StoreState;
|
||||
|
||||
|
||||
@@ -24,12 +22,9 @@ export const uiSlice = createSlice({
|
||||
setIsMobileScreen(state, action: PayloadAction<boolean>) {
|
||||
state.isMobileScreen = action.payload;
|
||||
},
|
||||
toggleSearch(state, action: PayloadAction<boolean | undefined>) {
|
||||
state.isSearchOpen = action.payload ?? !state.isSearchOpen;
|
||||
}
|
||||
},
|
||||
});
|
||||
|
||||
export const { setNavHeight, setIsMobileScreen, toggleSearch } = uiSlice.actions;
|
||||
export const { setNavHeight, setIsMobileScreen } = uiSlice.actions;
|
||||
|
||||
export default uiSlice.reducer;
|
||||
|
||||
Reference in New Issue
Block a user