All files / src/pages/main-page/project-folders ProjectCardDragLayer.tsx

16.12% Statements 5/31
8.69% Branches 2/23
50% Functions 1/2
16.66% Lines 4/24

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66                  178x 89x 89x                                     89x                                                                      
import { FolderInput } from "lucide-react";
import { motion, useReducedMotion } from "motion/react";
import { useDragLayer } from "react-dnd";
import {
  PROJECT_CARD_DRAG_TYPE,
  type ProjectCardDragItem,
} from "@/pages/main-page/project-folders/model";
 
/** Render a compact pointer-following preview instead of the full project card. */
export function ProjectCardDragLayer() {
  const shouldReduceMotion = useReducedMotion();
  const { currentOffset, isDragging, item, itemType } = useDragLayer<
    {
      currentOffset: { x: number; y: number } | null;
      isDragging: boolean;
      item: ProjectCardDragItem | null;
      itemType: string | symbol | null;
    },
    ProjectCardDragItem
  >((monitor) => ({
    currentOffset: monitor.getClientOffset(),
    isDragging: monitor.isDragging(),
    item: monitor.getItem(),
    itemType: monitor.getItemType(),
  }));
 
  if (
    !isDragging ||
    itemType !== PROJECT_CARD_DRAG_TYPE ||
    !item ||
    !currentOffset
  ) {
    return null;
  }
 
  return (
    <div
      className="pointer-events-none fixed left-0 top-0 z-[100] will-change-transform"
      style={{
        transform: `translate3d(${currentOffset.x + 16}px, ${currentOffset.y + 16}px, 0)`,
      }}
    >
      <motion.div
        role="status"
        aria-label={`Dragging ${item.projectName}`}
        initial={shouldReduceMotion ? false : { opacity: 0, scale: 0.94 }}
        animate={{ opacity: 1, scale: 1 }}
        transition={{ duration: shouldReduceMotion ? 0 : 0.1 }}
        className="flex min-w-44 max-w-56 items-center gap-2 rounded-md border border-border bg-popover px-3 py-2 text-popover-foreground shadow-lg"
      >
        <span className="flex h-8 w-8 shrink-0 items-center justify-center rounded-md bg-primary/10 text-primary">
          <FolderInput className="h-4 w-4" aria-hidden="true" />
        </span>
        <span className="min-w-0">
          <span className="block truncate text-sm font-medium">
            {item.projectName}
          </span>
          <span className="block text-xs text-muted-foreground">
            Move project
          </span>
        </span>
      </motion.div>
    </div>
  );
}