Добавлен новый компонент TabsNav для управления навигацией по вкладкам в страницах аккаунта и статистики. Обновлены соответствующие страницы для использования нового компонента, что улучшает структуру кода и упрощает управление вкладками. Также внесены изменения в стили для улучшения визуального восприятия.
This commit is contained in:
parent
14921074a5
commit
5614894e49
@ -23,6 +23,7 @@ import AccountProfile from "../../components/AccountProfile";
|
||||
import AccountSecurity from "../../components/AccountSecurity";
|
||||
import AccountNotifications from "../../components/AccountNotifications";
|
||||
import AccountAgentTransactionSection from "../../components/AccountAgentTransactionSection";
|
||||
import TabsNav from "../../components/TabsNav";
|
||||
|
||||
const initialNotifications = {
|
||||
emailNotifications: true,
|
||||
@ -54,22 +55,7 @@ export default function AccountPage() {
|
||||
<div className={styles.dashboard}>
|
||||
<h1 className={styles.title}>Аккаунт</h1>
|
||||
<div className={accountStyles.accountTabsNav}>
|
||||
<nav className={accountStyles.accountTabsNav}>
|
||||
{tabs.map(tab => (
|
||||
<button
|
||||
key={tab.id}
|
||||
onClick={() => setActiveTab(tab.id)}
|
||||
className={
|
||||
activeTab === tab.id
|
||||
? `${accountStyles.accountTabsButton} ${accountStyles.accountTabsButtonActive}`
|
||||
: accountStyles.accountTabsButton
|
||||
}
|
||||
>
|
||||
{tab.icon}
|
||||
{tab.label}
|
||||
</button>
|
||||
))}
|
||||
</nav>
|
||||
<TabsNav activeTab={activeTab} setActiveTab={setActiveTab} tabs={tabs} />
|
||||
</div>
|
||||
{activeTab === "profile" && (
|
||||
<AccountProfile />
|
||||
|
||||
@ -8,6 +8,7 @@ import styles from "../../styles/stat.module.css";
|
||||
import DateInput from "../../components/DateInput";
|
||||
import DateFilters from "../../components/DateFilters";
|
||||
import AuthGuard from "../../components/AuthGuard";
|
||||
import TabsNav from "../../components/TabsNav";
|
||||
|
||||
const tabs = [
|
||||
{ id: "agents", label: "Агенты" },
|
||||
@ -40,17 +41,7 @@ export default function StatPage() {
|
||||
<h1 className={styles.title}>Статистика и аналитика</h1>
|
||||
{/* <button className={styles.exportBtn}>Экспорт</button> */}
|
||||
</div>
|
||||
<div className={styles.tabs}>
|
||||
{tabs.map((tab) => (
|
||||
<button
|
||||
key={tab.id}
|
||||
className={activeTab === tab.id ? styles.activeTab : styles.tab}
|
||||
onClick={() => setActiveTab(tab.id)}
|
||||
>
|
||||
{tab.label}
|
||||
</button>
|
||||
))}
|
||||
</div>
|
||||
<TabsNav activeTab={activeTab} setActiveTab={setActiveTab} tabs={tabs} />
|
||||
|
||||
<DateFilters
|
||||
dateStart={filters.dateStart}
|
||||
|
||||
@ -1,4 +1,6 @@
|
||||
import React from "react";
|
||||
import { CalendarToday } from "@mui/icons-material";
|
||||
import styles from "../styles/dateinput.module.css";
|
||||
|
||||
interface DateInputProps {
|
||||
label: string;
|
||||
@ -11,13 +13,28 @@ interface DateInputProps {
|
||||
const DateInput: React.FC<DateInputProps> = ({ label, value, onChange, min, max }) => (
|
||||
<div>
|
||||
<label>{label}</label>
|
||||
<input
|
||||
type="date"
|
||||
value={value}
|
||||
onChange={onChange}
|
||||
min={min}
|
||||
max={max}
|
||||
/>
|
||||
<div style={{ position: "relative" }}>
|
||||
<input
|
||||
type="date"
|
||||
value={value}
|
||||
onChange={onChange}
|
||||
min={min}
|
||||
max={max}
|
||||
className={`${styles.dateInputHiddenIcon} ${styles.dateInputBase}`}
|
||||
/>
|
||||
<CalendarToday
|
||||
className={styles.dateIcon}
|
||||
fontSize="small"
|
||||
onClick={(e) => {
|
||||
const inputElement = e.currentTarget.previousElementSibling as HTMLInputElement;
|
||||
if (inputElement && typeof inputElement.showPicker === 'function') {
|
||||
inputElement.showPicker();
|
||||
} else {
|
||||
inputElement.focus();
|
||||
}
|
||||
}}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
|
||||
|
||||
@ -5,6 +5,8 @@ import styles from "../styles/navigation.module.css";
|
||||
import Cookies from "js-cookie";
|
||||
import { useEffect, useState } from "react";
|
||||
import { useUser } from "./UserContext";
|
||||
import TabsNav from "./TabsNav";
|
||||
import { useRouter } from "next/navigation";
|
||||
|
||||
interface NavItem {
|
||||
id: string;
|
||||
@ -22,6 +24,7 @@ const Navigation: React.FC = () => {
|
||||
const pathname = usePathname();
|
||||
const [login, setLogin] = useState<string>("");
|
||||
const { firstName, surname } = useUser();
|
||||
const router = useRouter();
|
||||
|
||||
useEffect(() => {
|
||||
if (typeof document !== "undefined") {
|
||||
@ -30,25 +33,21 @@ const Navigation: React.FC = () => {
|
||||
}
|
||||
}, []);
|
||||
|
||||
const handleNavigationChange = (tabId: string) => {
|
||||
if (tabId === "home") {
|
||||
router.push("/");
|
||||
} else if (tabId === "stat") {
|
||||
router.push("/stat");
|
||||
} else if (tabId === "billing") {
|
||||
router.push("/billing");
|
||||
}
|
||||
};
|
||||
|
||||
if (pathname === "/auth") return null;
|
||||
return (
|
||||
<nav className={styles.nav}>
|
||||
<div className={styles.logo}>RE:Premium Partner</div>
|
||||
<div className={styles.links}>
|
||||
{navItems.map((item) => (
|
||||
<Link
|
||||
key={item.id}
|
||||
href={item.href}
|
||||
className={
|
||||
pathname === item.href
|
||||
? styles.active
|
||||
: styles.link
|
||||
}
|
||||
>
|
||||
{item.label}
|
||||
</Link>
|
||||
))}
|
||||
</div>
|
||||
<TabsNav activeTab={pathname} setActiveTab={handleNavigationChange} tabs={navItems} />
|
||||
<div className={styles.profile}>
|
||||
<Link href="/account" style={{ display: 'flex', alignItems: 'center', gap: 12, textDecoration: 'none' }}>
|
||||
<div className={styles.avatar}>
|
||||
|
||||
71
src/components/TabsNav.tsx
Normal file
71
src/components/TabsNav.tsx
Normal file
@ -0,0 +1,71 @@
|
||||
import React from "react";
|
||||
import Link from "next/link";
|
||||
import defaultTabsStyles from "../styles/tabs.module.css";
|
||||
|
||||
interface TabItem {
|
||||
id: string;
|
||||
label: string;
|
||||
href?: string;
|
||||
icon?: React.ReactNode;
|
||||
}
|
||||
|
||||
interface TabsNavProps {
|
||||
activeTab: string;
|
||||
setActiveTab: (tabId: string) => void;
|
||||
tabs: TabItem[];
|
||||
tabStyles?: {
|
||||
nav: string;
|
||||
button: string;
|
||||
buttonActive: string;
|
||||
};
|
||||
}
|
||||
|
||||
const TabsNav: React.FC<TabsNavProps> = ({
|
||||
activeTab,
|
||||
setActiveTab,
|
||||
tabs,
|
||||
tabStyles,
|
||||
}) => {
|
||||
const currentTabStyles = tabStyles || {
|
||||
nav: defaultTabsStyles.tabsNav,
|
||||
button: defaultTabsStyles.tabButton,
|
||||
buttonActive: defaultTabsStyles.tabButtonActive,
|
||||
};
|
||||
|
||||
return (
|
||||
<nav className={currentTabStyles.nav}>
|
||||
{tabs.map((tab) => (
|
||||
tab.href ? (
|
||||
<Link
|
||||
key={tab.id}
|
||||
href={tab.href}
|
||||
onClick={() => setActiveTab(tab.id)}
|
||||
className={
|
||||
activeTab === tab.href
|
||||
? `${currentTabStyles.button} ${currentTabStyles.buttonActive}`
|
||||
: currentTabStyles.button
|
||||
}
|
||||
>
|
||||
{tab.icon}
|
||||
{tab.label}
|
||||
</Link>
|
||||
) : (
|
||||
<button
|
||||
key={tab.id}
|
||||
onClick={() => setActiveTab(tab.id)}
|
||||
className={
|
||||
activeTab === tab.id
|
||||
? `${currentTabStyles.button} ${currentTabStyles.buttonActive}`
|
||||
: currentTabStyles.button
|
||||
}
|
||||
>
|
||||
{tab.icon}
|
||||
{tab.label}
|
||||
</button>
|
||||
)
|
||||
))}
|
||||
</nav>
|
||||
);
|
||||
};
|
||||
|
||||
export default TabsNav;
|
||||
@ -258,6 +258,7 @@
|
||||
font-weight: 500;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 8px;
|
||||
cursor: pointer;
|
||||
margin-top: 8px;
|
||||
@ -273,6 +274,7 @@
|
||||
padding: 0;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
color: #6b7280;
|
||||
}
|
||||
|
||||
/* --- Стили для вкладки уведомлений --- */
|
||||
@ -362,9 +364,11 @@
|
||||
left: 22px;
|
||||
}
|
||||
|
||||
/* --- Стили для табов и навигации из page.tsx --- */
|
||||
|
||||
.accountTabsNav {
|
||||
|
||||
/* Стили для табов и навигации из page.tsx */
|
||||
|
||||
/* .accountTabsNav {
|
||||
display: flex;
|
||||
gap: 32px;
|
||||
border-bottom: 1px solid #e5e7eb;
|
||||
@ -389,51 +393,18 @@
|
||||
border-bottom: 2px solid #2563eb;
|
||||
color: #2563eb;
|
||||
font-weight: 600;
|
||||
}
|
||||
} */
|
||||
|
||||
/* Стили для кнопок подтверждения */
|
||||
.primaryButton {
|
||||
background-color: #2563eb; /* Синий */
|
||||
color: #ffffff;
|
||||
background: #2563eb;
|
||||
color: #fff;
|
||||
border: none;
|
||||
border-radius: 6px;
|
||||
padding: 8px 16px;
|
||||
padding: 8px 20px;
|
||||
font-weight: 500;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 8px;
|
||||
cursor: pointer;
|
||||
transition: background-color 0.2s ease;
|
||||
}
|
||||
|
||||
.primaryButton:hover {
|
||||
background-color: #1d4ed8;
|
||||
}
|
||||
|
||||
.secondaryButton {
|
||||
background-color: #f3f4f6; /* Серый */
|
||||
color: #374151;
|
||||
border: 1px solid #d1d5db;
|
||||
border-radius: 6px;
|
||||
padding: 8px 16px;
|
||||
font-weight: 500;
|
||||
cursor: pointer;
|
||||
transition: background-color 0.2s ease;
|
||||
}
|
||||
|
||||
.secondaryButton:hover {
|
||||
background-color: #e5e7eb;
|
||||
}
|
||||
|
||||
.tertiaryButton {
|
||||
background: none;
|
||||
color: #6b7280; /* Темно-серый */
|
||||
border: none;
|
||||
padding: 8px 16px;
|
||||
font-weight: 500;
|
||||
cursor: pointer;
|
||||
transition: color 0.2s ease;
|
||||
}
|
||||
|
||||
.tertiaryButton:hover {
|
||||
color: #4b5563;
|
||||
}
|
||||
|
||||
/* ... можно добавить другие стили по необходимости ... */
|
||||
37
src/styles/dateinput.module.css
Normal file
37
src/styles/dateinput.module.css
Normal file
@ -0,0 +1,37 @@
|
||||
.dateInputHiddenIcon {
|
||||
-webkit-appearance: none; /* Safari и Chrome */
|
||||
-moz-appearance: none; /* Firefox */
|
||||
appearance: none; /* Стандартное свойство */
|
||||
}
|
||||
|
||||
.dateInputHiddenIcon::-webkit-calendar-picker-indicator {
|
||||
display: none; /* Скрыть для WebKit-браузеров */
|
||||
}
|
||||
|
||||
.dateInputHiddenIcon::-moz-calendar-picker-indicator {
|
||||
display: none; /* Скрыть для Mozilla-браузеров */
|
||||
}
|
||||
|
||||
.dateInputHiddenIcon::-ms-calendar-picker-indicator {
|
||||
display: none; /* Скрыть для Internet Explorer/Edge */
|
||||
}
|
||||
|
||||
.dateInputBase {
|
||||
width: 100%;
|
||||
padding: 8px;
|
||||
border: 1px solid #e5e7eb;
|
||||
border-radius: 6px;
|
||||
margin-top: 4px;
|
||||
box-sizing: border-box;
|
||||
padding-right: 40px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.dateIcon {
|
||||
position: absolute;
|
||||
right: 8px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
cursor: pointer;
|
||||
color: #6b7280;
|
||||
}
|
||||
@ -13,7 +13,7 @@
|
||||
font-weight: bold;
|
||||
color: #2563eb;
|
||||
}
|
||||
.links {
|
||||
/* .links {
|
||||
display: flex;
|
||||
gap: 32px;
|
||||
}
|
||||
@ -34,7 +34,7 @@
|
||||
color: #2563eb;
|
||||
border-bottom: 2px solid #2563eb;
|
||||
font-weight: 600;
|
||||
}
|
||||
} */
|
||||
.profile {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
|
||||
@ -27,11 +27,14 @@
|
||||
.exportBtn:hover {
|
||||
background: #1d4ed8;
|
||||
}
|
||||
.tabs {
|
||||
/* Tabs */
|
||||
/* .tabs {
|
||||
display: flex;
|
||||
gap: 32px;
|
||||
border-bottom: 1.5px solid #e5e7eb;
|
||||
margin-bottom: 24px;
|
||||
}
|
||||
|
||||
.tab {
|
||||
background: none;
|
||||
border: none;
|
||||
@ -43,17 +46,19 @@
|
||||
cursor: pointer;
|
||||
transition: color 0.2s, border 0.2s;
|
||||
}
|
||||
|
||||
.tab:hover {
|
||||
color: #2563eb;
|
||||
border-bottom: 2px solid #dbeafe;
|
||||
}
|
||||
|
||||
.activeTab {
|
||||
color: #2563eb;
|
||||
border: none;
|
||||
border-bottom: 2px solid #2563eb;
|
||||
font-weight: 600;
|
||||
background: none;
|
||||
}
|
||||
} */
|
||||
.filters {
|
||||
display: grid;
|
||||
grid-template-columns: repeat(1, 1fr);
|
||||
|
||||
31
src/styles/tabs.module.css
Normal file
31
src/styles/tabs.module.css
Normal file
@ -0,0 +1,31 @@
|
||||
.tabsNav {
|
||||
display: flex;
|
||||
gap: 32px;
|
||||
border-bottom: 1px solid #e5e7eb;
|
||||
margin-bottom: 24px;
|
||||
}
|
||||
|
||||
.tabButton {
|
||||
background: none;
|
||||
border: none;
|
||||
border-bottom: 2px solid transparent;
|
||||
color: #6b7280;
|
||||
font-weight: 500;
|
||||
font-size: 16px;
|
||||
padding: 8px 0;
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.tabButton:hover {
|
||||
color: #2563eb;
|
||||
border-bottom: 2px solid #dbeafe;
|
||||
}
|
||||
|
||||
.tabButtonActive {
|
||||
border-bottom: 2px solid #2563eb;
|
||||
color: #2563eb;
|
||||
font-weight: 600;
|
||||
}
|
||||
Loading…
x
Reference in New Issue
Block a user