mirror of
https://github.com/mue/mue.git
synced 2026-07-17 14:04:09 +02:00
style(tooltip): New tooltip animation
This commit is contained in:
@@ -1,5 +1,6 @@
|
||||
import { useState, memo, useRef } from 'react';
|
||||
import { useFloating, flip, offset, shift } from '@floating-ui/react-dom';
|
||||
import { motion, AnimatePresence } from 'framer-motion';
|
||||
import './tooltip.scss';
|
||||
|
||||
function Tooltip({ children, title, style, placement, subtitle }) {
|
||||
@@ -17,7 +18,7 @@ function Tooltip({ children, title, style, placement, subtitle }) {
|
||||
|
||||
return (
|
||||
<>
|
||||
<div
|
||||
<motion.div
|
||||
className="tooltip"
|
||||
style={style}
|
||||
onMouseEnter={() => setShowTooltip(true)}
|
||||
@@ -26,29 +27,38 @@ function Tooltip({ children, title, style, placement, subtitle }) {
|
||||
onBlur={() => setShowTooltip(false)}
|
||||
ref={setReference}
|
||||
aria-describedby={tooltipId.current}
|
||||
initial={{ opacity: 0, scale: 0.95 }}
|
||||
animate={{ opacity: 1, scale: 1 }}
|
||||
transition={{ duration: 0.2 }}
|
||||
>
|
||||
{children}
|
||||
</div>
|
||||
{showTooltip && (
|
||||
<span
|
||||
ref={refs.setFloating}
|
||||
style={{
|
||||
position: strategy,
|
||||
top: y ?? '',
|
||||
left: x ?? '',
|
||||
display: 'flex',
|
||||
flexFlow: 'column',
|
||||
}}
|
||||
className="tooltipTitle"
|
||||
>
|
||||
{title}
|
||||
<span style={{ fontSize: '8px' }}>{subtitle}</span>
|
||||
</span>
|
||||
)}
|
||||
</motion.div>
|
||||
<AnimatePresence>
|
||||
{showTooltip && (
|
||||
<motion.span
|
||||
ref={refs.setFloating}
|
||||
style={{
|
||||
position: strategy,
|
||||
top: y ?? '',
|
||||
left: x ?? '',
|
||||
display: 'flex',
|
||||
flexFlow: 'column',
|
||||
}}
|
||||
className="tooltipTitle"
|
||||
initial={{ opacity: 0, y: 20 }}
|
||||
animate={{ opacity: 1, y: 0 }}
|
||||
exit={{ opacity: 0, y: 20 }}
|
||||
transition={{ duration: 0.2 }}
|
||||
>
|
||||
{title}
|
||||
<span style={{ fontSize: '8px' }}>{subtitle}</span>
|
||||
</motion.span>
|
||||
)}
|
||||
</AnimatePresence>
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
const MemoizedTooltip = memo(Tooltip);
|
||||
|
||||
export { MemoizedTooltip as default, MemoizedTooltip as Tooltip };
|
||||
export { MemoizedTooltip as default, MemoizedTooltip as Tooltip };
|
||||
@@ -33,9 +33,6 @@
|
||||
cursor: initial;
|
||||
user-select: none;
|
||||
opacity: 1;
|
||||
animation-name: floating;
|
||||
animation-duration: 0.3s;
|
||||
animation-timing-function: ease-in;
|
||||
}
|
||||
|
||||
#modal {
|
||||
@@ -54,26 +51,6 @@
|
||||
}
|
||||
}
|
||||
|
||||
.tooltipTitle::before {
|
||||
transform: scale3d(0.2, 0.2, 1);
|
||||
transition: all 0.2s ease-in-out;
|
||||
}
|
||||
|
||||
.tooltipTitle::after {
|
||||
transform: translate3d(0, 6px, 0);
|
||||
transition: all 0.1s ease-in-out;
|
||||
}
|
||||
|
||||
.tooltipTitle:hover::before,
|
||||
.tooltipTitle:hover::after {
|
||||
opacity: 1;
|
||||
transform: scale3d(1, 1, 1);
|
||||
}
|
||||
|
||||
.tooltipTitle:hover::after {
|
||||
transition: all 0.2s 0.1s ease-in-out;
|
||||
}
|
||||
|
||||
#arrow {
|
||||
position: absolute;
|
||||
background: #333;
|
||||
@@ -96,37 +73,3 @@
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#floating {
|
||||
transition-property: opacity, transform;
|
||||
}
|
||||
|
||||
#floating[data-status='open'],
|
||||
#floating[data-status='close'] {
|
||||
transition-duration: 250ms;
|
||||
}
|
||||
|
||||
#floating[data-status='initial'],
|
||||
#floating[data-status='close'] {
|
||||
opacity: 0;
|
||||
}
|
||||
|
||||
#floating[data-status='initial'][data-placement^='top'],
|
||||
#floating[data-status='close'][data-placement^='top'] {
|
||||
transform: translateY(5px);
|
||||
}
|
||||
|
||||
#floating[data-status='initial'][data-placement^='bottom'],
|
||||
#floating[data-status='close'][data-placement^='bottom'] {
|
||||
transform: translateY(-5px);
|
||||
}
|
||||
|
||||
#floating[data-status='initial'][data-placement^='left'],
|
||||
#floating[data-status='close'][data-placement^='left'] {
|
||||
transform: translateX(5px);
|
||||
}
|
||||
|
||||
#floating[data-status='initial'][data-placement^='right'],
|
||||
#floating[data-status='close'][data-placement^='right'] {
|
||||
transform: translateX(-5px);
|
||||
}
|
||||
|
||||
@@ -1,3 +1,21 @@
|
||||
const Panel = ({ children, type }) => <section className={type}>{children}</section>;
|
||||
import { motion, AnimatePresence } from 'framer-motion';
|
||||
|
||||
const Panel = ({ children, type }) => {
|
||||
let className;
|
||||
switch (type) {
|
||||
case 'aside':
|
||||
className = 'aside';
|
||||
break;
|
||||
case 'content':
|
||||
return (
|
||||
<section className="content">
|
||||
{children}
|
||||
</section>
|
||||
);
|
||||
default:
|
||||
className = type;
|
||||
}
|
||||
return <section className={className}>{children}</section>;
|
||||
};
|
||||
|
||||
export { Panel as default, Panel };
|
||||
|
||||
Reference in New Issue
Block a user