close profilecard on mouse leave
Some checks failed
continuous-integration/drone/pr Build is failing
Some checks failed
continuous-integration/drone/pr Build is failing
This commit is contained in:
parent
561ee94ab0
commit
a92fc267c3
@ -15,7 +15,6 @@
|
||||
"@snort/system-wasm": "workspace:*",
|
||||
"@snort/system-web": "workspace:*",
|
||||
"@szhsin/react-menu": "^3.3.1",
|
||||
"@uidotdev/usehooks": "^2.3.1",
|
||||
"@void-cat/api": "^1.0.10",
|
||||
"classnames": "^2.3.2",
|
||||
"debug": "^4.3.4",
|
||||
|
@ -1,25 +1,35 @@
|
||||
import { NostrLink, NostrPrefix } from "@snort/system";
|
||||
import { useUserProfile } from "@snort/system-react";
|
||||
import { useHover } from "@uidotdev/usehooks";
|
||||
|
||||
import DisplayName from "@/Element/User/DisplayName";
|
||||
import { ProfileCard } from "@/Element/User/ProfileCard";
|
||||
import { ProfileLink } from "@/Element/User/ProfileLink";
|
||||
import { useCallback, useRef, useState } from "react";
|
||||
|
||||
export default function Mention({ link }: { link: NostrLink }) {
|
||||
const [ref, hovering] = useHover<HTMLAnchorElement>();
|
||||
const profile = useUserProfile(link.id);
|
||||
const [isHovering, setIsHovering] = useState(false);
|
||||
|
||||
const hoverTimeoutRef = useRef<NodeJS.Timeout | null>(null);
|
||||
|
||||
const handleMouseEnter = useCallback(() => {
|
||||
hoverTimeoutRef.current && clearTimeout(hoverTimeoutRef.current);
|
||||
hoverTimeoutRef.current = setTimeout(() => setIsHovering(true), 100); // Adjust timeout as needed
|
||||
}, []);
|
||||
|
||||
const handleMouseLeave = useCallback(() => {
|
||||
hoverTimeoutRef.current && clearTimeout(hoverTimeoutRef.current);
|
||||
hoverTimeoutRef.current = setTimeout(() => setIsHovering(false), 300); // Adjust timeout as needed
|
||||
}, []);
|
||||
|
||||
if (link.type !== NostrPrefix.Profile && link.type !== NostrPrefix.PublicKey) return;
|
||||
|
||||
return (
|
||||
<>
|
||||
<span className="highlight" onMouseEnter={handleMouseEnter} onMouseLeave={handleMouseLeave}>
|
||||
<ProfileLink pubkey={link.id} link={link} user={profile} onClick={e => e.stopPropagation()}>
|
||||
<span ref={ref}>
|
||||
@<DisplayName user={profile} pubkey={link.id} />
|
||||
</span>
|
||||
</ProfileLink>
|
||||
<ProfileCard pubkey={link.id} user={profile} show={hovering} ref={ref} />
|
||||
</>
|
||||
{isHovering && <ProfileCard pubkey={link.id} user={profile} show={true} />}
|
||||
</span>
|
||||
);
|
||||
}
|
||||
|
@ -10,28 +10,15 @@ import Text from "@/Element/Text";
|
||||
import { useEffect, useState } from "react";
|
||||
import useLogin from "../../Hooks/useLogin";
|
||||
|
||||
interface RectElement {
|
||||
getBoundingClientRect(): {
|
||||
left: number;
|
||||
right: number;
|
||||
top: number;
|
||||
bottom: number;
|
||||
width: number;
|
||||
height: number;
|
||||
};
|
||||
}
|
||||
|
||||
export function ProfileCard({
|
||||
pubkey,
|
||||
user,
|
||||
show,
|
||||
ref,
|
||||
delay,
|
||||
}: {
|
||||
pubkey: string;
|
||||
user?: UserMetadata;
|
||||
show: boolean;
|
||||
ref: React.RefObject<Element | RectElement>;
|
||||
delay?: number;
|
||||
}) {
|
||||
const [showProfileMenu, setShowProfileMenu] = useState(false);
|
||||
@ -56,7 +43,6 @@ export function ProfileCard({
|
||||
return (
|
||||
<ControlledMenu
|
||||
state={showProfileMenu ? "open" : "closed"}
|
||||
anchorRef={ref}
|
||||
menuClassName="profile-card"
|
||||
onClose={() => setShowProfileMenu(false)}
|
||||
align="end">
|
||||
|
@ -1,9 +1,8 @@
|
||||
import "./ProfileImage.css";
|
||||
|
||||
import React, { ReactNode } from "react";
|
||||
import React, { ReactNode, useCallback, useRef, useState } from "react";
|
||||
import { HexKey, socialGraphInstance, UserMetadata } from "@snort/system";
|
||||
import { useUserProfile } from "@snort/system-react";
|
||||
import { useHover } from "@uidotdev/usehooks";
|
||||
import classNames from "classnames";
|
||||
|
||||
import Avatar from "@/Element/User/Avatar";
|
||||
@ -51,7 +50,19 @@ export default function ProfileImage({
|
||||
const user = useUserProfile(profile ? "" : pubkey) ?? profile;
|
||||
const nip05 = defaultNip ? defaultNip : user?.nip05;
|
||||
const followDistance = socialGraphInstance.getFollowDistance(pubkey);
|
||||
const [ref, hovering] = useHover<HTMLDivElement>();
|
||||
const [isHovering, setIsHovering] = useState(false);
|
||||
|
||||
const hoverTimeoutRef = useRef<NodeJS.Timeout | null>(null);
|
||||
|
||||
const handleMouseEnter = useCallback(() => {
|
||||
hoverTimeoutRef.current && clearTimeout(hoverTimeoutRef.current);
|
||||
hoverTimeoutRef.current = setTimeout(() => setIsHovering(true), 100); // Adjust timeout as needed
|
||||
}, []);
|
||||
|
||||
const handleMouseLeave = useCallback(() => {
|
||||
hoverTimeoutRef.current && clearTimeout(hoverTimeoutRef.current);
|
||||
hoverTimeoutRef.current = setTimeout(() => setIsHovering(false), 300); // Adjust timeout as needed
|
||||
}, []);
|
||||
|
||||
function handleClick(e: React.MouseEvent) {
|
||||
if (link === "") {
|
||||
@ -69,7 +80,7 @@ export default function ProfileImage({
|
||||
}
|
||||
return (
|
||||
<>
|
||||
<div className="avatar-wrapper" ref={ref}>
|
||||
<div className="avatar-wrapper" onMouseEnter={handleMouseEnter}>
|
||||
<Avatar
|
||||
pubkey={pubkey}
|
||||
user={user}
|
||||
@ -103,8 +114,12 @@ export default function ProfileImage({
|
||||
}
|
||||
|
||||
function profileCard() {
|
||||
if ((showProfileCard ?? true) && user) {
|
||||
return <ProfileCard pubkey={pubkey} user={user} show={hovering} ref={ref} />;
|
||||
if ((showProfileCard ?? true) && user && isHovering) {
|
||||
return (
|
||||
<div className="absolute shadow-lg z-10">
|
||||
<ProfileCard pubkey={pubkey} user={user} show={true} />
|
||||
</div>
|
||||
);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
@ -120,7 +135,7 @@ export default function ProfileImage({
|
||||
);
|
||||
} else {
|
||||
return (
|
||||
<>
|
||||
<div className="relative" onMouseLeave={handleMouseLeave}>
|
||||
<ProfileLink
|
||||
pubkey={pubkey}
|
||||
className={classNames("pfp", className)}
|
||||
@ -130,7 +145,7 @@ export default function ProfileImage({
|
||||
{inner()}
|
||||
</ProfileLink>
|
||||
{profileCard()}
|
||||
</>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user