mirror of
https://github.com/OpenCut-app/OpenCut.git
synced 2026-07-13 21:52:53 +02:00
fix: handlers component on mobile
This commit is contained in:
@@ -19,6 +19,7 @@ export function Handlebars({
|
|||||||
const [leftHandle, setLeftHandle] = useState(0);
|
const [leftHandle, setLeftHandle] = useState(0);
|
||||||
const [rightHandle, setRightHandle] = useState(maxWidth);
|
const [rightHandle, setRightHandle] = useState(maxWidth);
|
||||||
const [contentWidth, setContentWidth] = useState(maxWidth);
|
const [contentWidth, setContentWidth] = useState(maxWidth);
|
||||||
|
const [isDragging, setIsDragging] = useState(false);
|
||||||
|
|
||||||
const leftHandleX = useMotionValue(0);
|
const leftHandleX = useMotionValue(0);
|
||||||
const rightHandleX = useMotionValue(maxWidth);
|
const rightHandleX = useMotionValue(maxWidth);
|
||||||
@@ -33,6 +34,27 @@ export function Handlebars({
|
|||||||
const containerRef = useRef<HTMLDivElement>(null);
|
const containerRef = useRef<HTMLDivElement>(null);
|
||||||
const measureRef = useRef<HTMLDivElement>(null);
|
const measureRef = useRef<HTMLDivElement>(null);
|
||||||
|
|
||||||
|
// Prevent scroll when dragging on mobile
|
||||||
|
useEffect(() => {
|
||||||
|
const preventDefault = (e: TouchEvent) => {
|
||||||
|
if (isDragging) {
|
||||||
|
e.preventDefault();
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
if (isDragging) {
|
||||||
|
document.addEventListener("touchmove", preventDefault, {
|
||||||
|
passive: false,
|
||||||
|
});
|
||||||
|
document.body.style.overflow = "hidden";
|
||||||
|
}
|
||||||
|
|
||||||
|
return () => {
|
||||||
|
document.removeEventListener("touchmove", preventDefault);
|
||||||
|
document.body.style.overflow = "";
|
||||||
|
};
|
||||||
|
}, [isDragging]);
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
if (!measureRef.current) return;
|
if (!measureRef.current) return;
|
||||||
|
|
||||||
@@ -80,6 +102,14 @@ export function Handlebars({
|
|||||||
setRightHandle(newRight);
|
setRightHandle(newRight);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
const handleDragStart = () => {
|
||||||
|
setIsDragging(true);
|
||||||
|
};
|
||||||
|
|
||||||
|
const handleDragEnd = () => {
|
||||||
|
setIsDragging(false);
|
||||||
|
};
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className="flex justify-center gap-4 leading-[4rem] mt-0 md:mt-2">
|
<div className="flex justify-center gap-4 leading-[4rem] mt-0 md:mt-2">
|
||||||
<div
|
<div
|
||||||
@@ -95,8 +125,10 @@ export function Handlebars({
|
|||||||
style={{ width: contentWidth }}
|
style={{ width: contentWidth }}
|
||||||
>
|
>
|
||||||
<div className="absolute inset-0 w-full h-full rounded-2xl border border-yellow-500 flex justify-between">
|
<div className="absolute inset-0 w-full h-full rounded-2xl border border-yellow-500 flex justify-between">
|
||||||
|
{/* Left Handle */}
|
||||||
<motion.div
|
<motion.div
|
||||||
className="h-full border border-yellow-500 w-7 rounded-full bg-accent flex items-center justify-center cursor-ew-resize select-none"
|
className="h-full border border-yellow-500 rounded-full bg-accent flex items-center justify-center cursor-ew-resize select-none touch-none
|
||||||
|
w-9 md:w-7 min-h-[44px] md:min-h-0"
|
||||||
style={{
|
style={{
|
||||||
position: "absolute",
|
position: "absolute",
|
||||||
x: leftHandleX,
|
x: leftHandleX,
|
||||||
@@ -108,19 +140,24 @@ export function Handlebars({
|
|||||||
dragElastic={0}
|
dragElastic={0}
|
||||||
dragMomentum={false}
|
dragMomentum={false}
|
||||||
onDrag={handleLeftDrag}
|
onDrag={handleLeftDrag}
|
||||||
|
onDragStart={handleDragStart}
|
||||||
|
onDragEnd={handleDragEnd}
|
||||||
whileHover={{ scale: 1.05 }}
|
whileHover={{ scale: 1.05 }}
|
||||||
whileDrag={{ scale: 1.1 }}
|
whileDrag={{ scale: 1.1 }}
|
||||||
|
whileTap={{ scale: 1.1 }}
|
||||||
transition={{ type: "spring", stiffness: 400, damping: 30 }}
|
transition={{ type: "spring", stiffness: 400, damping: 30 }}
|
||||||
>
|
>
|
||||||
<div className="w-2 h-8 rounded-full bg-yellow-500"></div>
|
<div className="w-2 h-8 rounded-full bg-yellow-500"></div>
|
||||||
</motion.div>
|
</motion.div>
|
||||||
|
|
||||||
|
{/* Right Handle */}
|
||||||
<motion.div
|
<motion.div
|
||||||
className="h-full border border-yellow-500 w-7 rounded-full bg-accent flex items-center justify-center cursor-ew-resize select-none"
|
className="h-full border border-yellow-500 rounded-full bg-accent flex items-center justify-center cursor-ew-resize select-none touch-none
|
||||||
|
w-9 md:w-7 min-h-[44px] md:min-h-0"
|
||||||
style={{
|
style={{
|
||||||
position: "absolute",
|
position: "absolute",
|
||||||
x: rightHandleX,
|
x: rightHandleX,
|
||||||
left: -30,
|
left: -36, // Adjusted for larger mobile handle
|
||||||
zIndex: 10,
|
zIndex: 10,
|
||||||
}}
|
}}
|
||||||
drag="x"
|
drag="x"
|
||||||
@@ -131,8 +168,11 @@ export function Handlebars({
|
|||||||
dragElastic={0}
|
dragElastic={0}
|
||||||
dragMomentum={false}
|
dragMomentum={false}
|
||||||
onDrag={handleRightDrag}
|
onDrag={handleRightDrag}
|
||||||
|
onDragStart={handleDragStart}
|
||||||
|
onDragEnd={handleDragEnd}
|
||||||
whileHover={{ scale: 1.05 }}
|
whileHover={{ scale: 1.05 }}
|
||||||
whileDrag={{ scale: 1.1 }}
|
whileDrag={{ scale: 1.1 }}
|
||||||
|
whileTap={{ scale: 1.1 }}
|
||||||
transition={{ type: "spring", stiffness: 400, damping: 30 }}
|
transition={{ type: "spring", stiffness: 400, damping: 30 }}
|
||||||
>
|
>
|
||||||
<div className="w-2 h-8 rounded-full bg-yellow-500"></div>
|
<div className="w-2 h-8 rounded-full bg-yellow-500"></div>
|
||||||
@@ -161,4 +201,4 @@ export function Handlebars({
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
};
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user