From 620f4a7f9072cabbd061ae4c2ce1812c70ef5085 Mon Sep 17 00:00:00 2001 From: mawkone Date: Tue, 19 May 2026 19:00:07 -0700 Subject: [PATCH] feat(ui): redesign Plan tab with Objective, User Stories, Features, and Architecture panels --- .../project/[projectId]/(home)/plan/page.tsx | 193 +++++++++++++++++- 1 file changed, 182 insertions(+), 11 deletions(-) diff --git a/vibn-frontend/app/[workspace]/project/[projectId]/(home)/plan/page.tsx b/vibn-frontend/app/[workspace]/project/[projectId]/(home)/plan/page.tsx index 6212c90c..93d69847 100644 --- a/vibn-frontend/app/[workspace]/project/[projectId]/(home)/plan/page.tsx +++ b/vibn-frontend/app/[workspace]/project/[projectId]/(home)/plan/page.tsx @@ -181,22 +181,193 @@ function ObjectiveView({ plan, projectId, onChange }: { plan: Plan, projectId: s // ────────────────────────────────────────────────── // 2. USER STORIES VIEW // ────────────────────────────────────────────────── -function UserStoriesView({ plan, projectId }: { plan: Plan, projectId: string, onChange: (p: Plan) => void }) { - // In a full implementation, we'd parse spec.md or filter specific types of tasks. - // For now, we mock the UI to show the intended architecture. +// MOCK DATA: In production, this would be parsed from the AI's spec markdown or a JSON array in the database. +const MOCK_JOURNEYS = [ + { + id: "j1", + name: "User Dashboard", + persona: "👑 Admin", + goal: "Provides a centralized view of all active jobs, metrics, and pending approvals.", + stories: [ + { + id: "s1", + title: "View active jobs", + description: "As an Admin, I want to see a map of today's jobs so I know where my team is.", + criteria: [ + { text: "Map centers on user's GPS location.", done: false }, + { text: "Clicking a pin opens a detail modal.", done: true } + ] + }, + { + id: "s2", + title: "Approve pending payouts", + description: "As an Admin, I want to review completed jobs and click 'Approve' to trigger Stripe payouts.", + criteria: [ + { text: "List displays jobs with 'completed' status.", done: false }, + { text: "Approve button triggers success toast.", done: false } + ] + } + ] + }, + { + id: "j2", + name: "Authentication & Onboarding", + persona: "👤 Customer", + goal: "Allows a new user to securely create an account and fill out their initial profile.", + stories: [ + { + id: "s3", + title: "Sign up via Email", + description: "As a Customer, I want to sign up with my email and a password so my data is secure.", + criteria: [ + { text: "Form validates email format.", done: false }, + { text: "Password must be > 8 characters.", done: false } + ] + } + ] + } +]; + +function UserStoriesView({ plan, projectId, onChange }: { plan: Plan, projectId: string, onChange: (p: Plan) => void }) { + const [activeJourneyId, setActiveJourneyId] = useState(MOCK_JOURNEYS[0].id); + const activeJourney = MOCK_JOURNEYS.find(j => j.id === activeJourneyId); + return ( -
+

User Stories

The prioritized journeys users will take through your application.

- -
- -

User Stories are being built.

-

- This view will display specific user personas and their acceptance scenarios (e.g. "As a User, I want to log in so I can see my dashboard"). -

+ +
+ + {/* LEFT COLUMN: The Index */} +
+ {MOCK_JOURNEYS.map(j => { + const isActive = j.id === activeJourneyId; + return ( + + ); + })} + + +
+ + {/* RIGHT COLUMN: The Details */} +
+ {activeJourney ? ( + <> +
+
+

+ {activeJourney.name} +

+ + {activeJourney.persona} + +
+

+ Goal: {activeJourney.goal} +

+
+ +
+ {activeJourney.stories.map((story, i) => ( +
+
+ US{i + 1} +

{story.title}

+
+

+ "{story.description}" +

+ +
+
+ Acceptance Criteria +
+
    + {story.criteria.map((c, idx) => ( +
  • +
    + {c.done && } +
    + + {c.text} + +
  • + ))} +
+
+
+ ))} +
+ + ) : ( +
Select a journey to view stories
+ )} +
+
);