diff --git a/app/page.tsx b/app/page.tsx
index b7d81a4..d419706 100644
--- a/app/page.tsx
+++ b/app/page.tsx
@@ -2,11 +2,13 @@
import Link from "next/link";
import { Puzzle, Timer, Sparkles, Settings } from "lucide-react";
+import { useQueryClient } from "@tanstack/react-query";
import { StatusCard } from "@/components/StatusCard";
import { StatsCard } from "@/components/StatsCard";
import { SessionCard } from "@/components/SessionCard";
import { MemorySnapshotCard } from "@/components/MemorySnapshotCard";
import { useSessions } from "@/lib/hooks";
+import { usePullToRefresh } from "@/lib/usePullToRefresh";
const QUICK_LINKS = [
{ href: "/skills", label: "Skills", icon: Puzzle, color: "#a78bfa" },
@@ -16,8 +18,13 @@ const QUICK_LINKS = [
] as const;
export default function PulsePage() {
+ const qc = useQueryClient();
const { data: sessionsData, isLoading } = useSessions(8);
+ usePullToRefresh(() => {
+ qc.invalidateQueries();
+ });
+
return (
diff --git a/lib/usePullToRefresh.ts b/lib/usePullToRefresh.ts
new file mode 100644
index 0000000..a34103a
--- /dev/null
+++ b/lib/usePullToRefresh.ts
@@ -0,0 +1,36 @@
+"use client";
+
+import { useRef, useEffect, useCallback } from "react";
+
+export function usePullToRefresh(onRefresh: () => Promise | void) {
+ const startY = useRef(0);
+ const pulling = useRef(false);
+
+ const handleTouchStart = useCallback((e: TouchEvent) => {
+ if (window.scrollY === 0) {
+ startY.current = e.touches[0].clientY;
+ pulling.current = true;
+ }
+ }, []);
+
+ const handleTouchEnd = useCallback(
+ (e: TouchEvent) => {
+ if (!pulling.current) return;
+ pulling.current = false;
+ const diff = e.changedTouches[0].clientY - startY.current;
+ if (diff > 80) {
+ onRefresh();
+ }
+ },
+ [onRefresh]
+ );
+
+ useEffect(() => {
+ document.addEventListener("touchstart", handleTouchStart, { passive: true });
+ document.addEventListener("touchend", handleTouchEnd, { passive: true });
+ return () => {
+ document.removeEventListener("touchstart", handleTouchStart);
+ document.removeEventListener("touchend", handleTouchEnd);
+ };
+ }, [handleTouchStart, handleTouchEnd]);
+}