feat: Implement custom scrollbar, refine agent profile edit navigation, and enhance quick link scrolling on the agent edit page.
This commit is contained in:
@@ -1,6 +1,7 @@
|
||||
'use client';
|
||||
|
||||
import Image from 'next/image';
|
||||
import Link from 'next/link';
|
||||
import { Tag } from './Tag';
|
||||
|
||||
interface ProfileCardProps {
|
||||
@@ -47,14 +48,14 @@ export function ProfileCard({
|
||||
</span>
|
||||
</>
|
||||
)}
|
||||
<button className="p-1 hover:bg-gray-100 rounded transition-colors">
|
||||
<Link href="/agent/edit" className="p-1 hover:bg-gray-100 rounded transition-colors">
|
||||
<Image
|
||||
src="/assets/icons/edit-pencil-orange-icon.svg"
|
||||
alt="Edit name"
|
||||
alt="Edit profile"
|
||||
width={16}
|
||||
height={16}
|
||||
/>
|
||||
</button>
|
||||
</Link>
|
||||
</div>
|
||||
<p className="text-[#00293d] text-sm mb-2 font-fractul">{title}</p>
|
||||
<div className="flex items-center justify-center lg:justify-start gap-4 text-sm text-[#00293d] font-fractul">
|
||||
|
||||
@@ -2,7 +2,6 @@
|
||||
|
||||
import { useSession } from 'next-auth/react';
|
||||
import Image from 'next/image';
|
||||
import Link from 'next/link';
|
||||
|
||||
// Import components from component folder
|
||||
import {
|
||||
@@ -104,17 +103,14 @@ export default function AgentDashboard() {
|
||||
<div className="absolute inset-0 bg-gradient-to-t from-black/50 via-black/20 to-transparent pointer-events-none" />
|
||||
</div>
|
||||
{/* Edit Icon - Top Right Outside */}
|
||||
<Link
|
||||
href="/agent/edit"
|
||||
className="absolute -top-3 -right-3 w-9 h-9 bg-white rounded-[10px] shadow-md flex items-center justify-center hover:bg-gray-50 transition-colors"
|
||||
>
|
||||
<button className="absolute -top-3 -right-3 w-9 h-9 bg-white rounded-[10px] shadow-md flex items-center justify-center hover:bg-gray-50 transition-colors">
|
||||
<Image
|
||||
src="/assets/icons/edit-icon.svg"
|
||||
alt="Edit profile"
|
||||
alt="Edit profile image"
|
||||
width={20}
|
||||
height={20}
|
||||
/>
|
||||
</Link>
|
||||
</button>
|
||||
</div>
|
||||
|
||||
{/* Status Buttons */}
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
'use client';
|
||||
|
||||
import { useState } from 'react';
|
||||
import { useEffect, useState, useRef } from 'react';
|
||||
|
||||
const links = [
|
||||
{ id: 'basic-info', label: 'Basic Information' },
|
||||
@@ -20,14 +20,65 @@ const links = [
|
||||
{ id: 'availability', label: 'Availability' },
|
||||
];
|
||||
|
||||
export function QuickLinks() {
|
||||
interface QuickLinksProps {
|
||||
scrollContainerRef: React.RefObject<HTMLDivElement | null>;
|
||||
}
|
||||
|
||||
export function QuickLinks({ scrollContainerRef }: QuickLinksProps) {
|
||||
const [activeLink, setActiveLink] = useState('basic-info');
|
||||
const isClickScrolling = useRef(false);
|
||||
|
||||
useEffect(() => {
|
||||
const container = scrollContainerRef.current;
|
||||
if (!container) return;
|
||||
|
||||
const handleScroll = () => {
|
||||
if (isClickScrolling.current) return;
|
||||
|
||||
const containerRect = container.getBoundingClientRect();
|
||||
const containerTop = containerRect.top;
|
||||
|
||||
let currentSection = 'basic-info';
|
||||
|
||||
for (const link of links) {
|
||||
const element = document.getElementById(link.id);
|
||||
if (element) {
|
||||
const rect = element.getBoundingClientRect();
|
||||
// Check if the section is near the top of the container
|
||||
if (rect.top <= containerTop + 100) {
|
||||
currentSection = link.id;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
setActiveLink(currentSection);
|
||||
};
|
||||
|
||||
container.addEventListener('scroll', handleScroll);
|
||||
return () => container.removeEventListener('scroll', handleScroll);
|
||||
}, [scrollContainerRef]);
|
||||
|
||||
const scrollToSection = (id: string) => {
|
||||
setActiveLink(id);
|
||||
const container = scrollContainerRef.current;
|
||||
const element = document.getElementById(id);
|
||||
if (element) {
|
||||
element.scrollIntoView({ behavior: 'smooth', block: 'start' });
|
||||
|
||||
if (element && container) {
|
||||
isClickScrolling.current = true;
|
||||
setActiveLink(id);
|
||||
|
||||
const containerRect = container.getBoundingClientRect();
|
||||
const elementRect = element.getBoundingClientRect();
|
||||
const scrollTop = container.scrollTop + (elementRect.top - containerRect.top) - 20;
|
||||
|
||||
container.scrollTo({
|
||||
top: scrollTop,
|
||||
behavior: 'smooth'
|
||||
});
|
||||
|
||||
// Reset the flag after scroll animation completes
|
||||
setTimeout(() => {
|
||||
isClickScrolling.current = false;
|
||||
}, 500);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
'use client';
|
||||
|
||||
import { useState } from 'react';
|
||||
import { useState, useRef } from 'react';
|
||||
import { useRouter } from 'next/navigation';
|
||||
import Image from 'next/image';
|
||||
import {
|
||||
@@ -108,6 +108,7 @@ const initialFormData = {
|
||||
export default function EditProfilePage() {
|
||||
const router = useRouter();
|
||||
const [formData, setFormData] = useState(initialFormData);
|
||||
const scrollContainerRef = useRef<HTMLDivElement>(null);
|
||||
|
||||
const handleCancel = () => {
|
||||
router.push('/agent/dashboard');
|
||||
@@ -124,16 +125,14 @@ export default function EditProfilePage() {
|
||||
};
|
||||
|
||||
return (
|
||||
<div className="flex gap-6">
|
||||
<div className="flex gap-6 h-[calc(100vh-180px)]">
|
||||
{/* Left Sidebar - Quick Links */}
|
||||
<div className="w-[220px] flex-shrink-0 hidden lg:block">
|
||||
<div className="sticky top-6">
|
||||
<QuickLinks />
|
||||
</div>
|
||||
<div className="w-[220px] flex-shrink-0 hidden lg:block h-full overflow-y-auto scrollbar-thin">
|
||||
<QuickLinks scrollContainerRef={scrollContainerRef} />
|
||||
</div>
|
||||
|
||||
{/* Main Content */}
|
||||
<div className="flex-1 space-y-6">
|
||||
{/* Main Content - Scrollable */}
|
||||
<div ref={scrollContainerRef} className="flex-1 space-y-6 overflow-y-auto pr-2 scrollbar-thin scrollbar-thumb-gray-300 scrollbar-track-transparent">
|
||||
{/* Basic Information */}
|
||||
<div className="bg-white rounded-[20px] p-6">
|
||||
<FormSection id="basic-info" icon="/assets/icons/user-icon.svg" title="Basic Information">
|
||||
|
||||
@@ -95,3 +95,27 @@ html {
|
||||
background-color: var(--color-primary-light);
|
||||
color: var(--color-primary-dark);
|
||||
}
|
||||
|
||||
/* Custom Scrollbar Styles */
|
||||
.scrollbar-thin::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.scrollbar-thin::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.scrollbar-thin::-webkit-scrollbar-thumb {
|
||||
background-color: #d1d5db;
|
||||
border-radius: 3px;
|
||||
}
|
||||
|
||||
.scrollbar-thin::-webkit-scrollbar-thumb:hover {
|
||||
background-color: #9ca3af;
|
||||
}
|
||||
|
||||
/* Firefox scrollbar */
|
||||
.scrollbar-thin {
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: #d1d5db transparent;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user