feat: Add character names to scenarios and UI

Introduces `characterName` to the `Scenario` type, enabling AI personas to be explicitly named. This change also updates the `ScenarioCard` component to display the character name and adds foundational support for potential future scenario deletion functionality. The README has been updated with a new AI Studio link.
This commit is contained in:
John Remillard committed 2026-03-04 11:43:39 -05:00
1 parent e92c489db5
commit a4946ed04d
18 files changed
+3585 -320

No files matched your search

+34 -6
View File
@@ -1,5 +1,5 @@
import React, { useState, useEffect } from 'react';
import React, { useState, useEffect, useCallback } from 'react';
import { SCENARIOS } from './constants';
import { Scenario, SessionMode, UserSettings } from './types';
import ScenarioCard from './components/ScenarioCard';
@@ -17,26 +17,44 @@ const DEFAULT_SETTINGS: UserSettings = {
genderPreference: 'Neutral'
};
const CUSTOM_SCENARIOS_KEY = 'cognitive-clarity-custom-scenarios';
const SETTINGS_KEY = 'cognitive-clarity-settings';
const App: React.FC = () => {
const [activeScenario, setActiveScenario] = useState<Scenario | null>(null);
const [sessionMode, setSessionMode] = useState<SessionMode>('text');
const [selectedDifficulty, setSelectedDifficulty] = useState<string>('All');
const [isPreparing, setIsPreparing] = useState(false);
// Custom Scenarios State
const [customScenarios, setCustomScenarios] = useState<Scenario[]>([]);
// Custom Scenarios State with LocalStorage persistence
const [customScenarios, setCustomScenarios] = useState<Scenario[]>(() => {
try {
const saved = localStorage.getItem(CUSTOM_SCENARIOS_KEY);
return saved ? JSON.parse(saved) : [];
} catch (e) {
console.error("Failed to load custom scenarios", e);
return [];
}
});
const [showGenerator, setShowGenerator] = useState(false);
const [showReference, setShowReference] = useState(false);
const [showSettings, setShowSettings] = useState(false);
// User Settings State
const [userSettings, setUserSettings] = useState<UserSettings>(() => {
const saved = localStorage.getItem('cognitive-clarity-settings');
const saved = localStorage.getItem(SETTINGS_KEY);
return saved ? JSON.parse(saved) : DEFAULT_SETTINGS;
});
// Save scenarios whenever they change
useEffect(() => {
localStorage.setItem('cognitive-clarity-settings', JSON.stringify(userSettings));
localStorage.setItem(CUSTOM_SCENARIOS_KEY, JSON.stringify(customScenarios));
}, [customScenarios]);
// Save settings whenever they change
useEffect(() => {
localStorage.setItem(SETTINGS_KEY, JSON.stringify(userSettings));
}, [userSettings]);
const handleSelectScenario = (scenario: Scenario, mode: SessionMode) => {
@@ -57,6 +75,10 @@ const App: React.FC = () => {
setShowGenerator(false);
};
const handleDeleteScenario = useCallback((id: string) => {
setCustomScenarios(prev => prev.filter(s => s.id !== id));
}, []);
const allScenarios = [...customScenarios, ...SCENARIOS];
const filteredScenarios = allScenarios.filter(scenario =>
selectedDifficulty === 'All' || scenario.difficulty === selectedDifficulty
@@ -125,6 +147,7 @@ const App: React.FC = () => {
scenario={activeScenario}
onExit={handleExitSession}
voiceSettings={userSettings}
onUpdateSettings={setUserSettings}
/>
</div>
)}
@@ -233,7 +256,12 @@ const App: React.FC = () => {
<div className="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-6">
{filteredScenarios.map(scenario => (
<ScenarioCard key={scenario.id} scenario={scenario} onSelect={handleSelectScenario} />
<ScenarioCard
key={scenario.id}
scenario={scenario}
onSelect={handleSelectScenario}
onDelete={scenario.id.startsWith('custom-') ? handleDeleteScenario : undefined}
/>
))}
<button
onClick={() => setShowGenerator(true)}