import { open } from "@tauri-apps/plugin-dialog"; import { Coffee, Download, FileJson, Loader2, RefreshCw, Upload, } from "lucide-react"; import { useEffect, useState } from "react"; import { toast } from "sonner"; import { Badge } from "@/components/ui/badge"; import { Button } from "@/components/ui/button"; import { Card, CardContent, CardHeader, CardTitle } from "@/components/ui/card"; import { Checkbox } from "@/components/ui/checkbox"; import { Dialog, DialogContent, DialogDescription, DialogFooter, DialogHeader, DialogTitle, } from "@/components/ui/dialog"; import { Input } from "@/components/ui/input"; import { Label } from "@/components/ui/label"; import { ScrollArea } from "@/components/ui/scroll-area"; import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue, } from "@/components/ui/select"; import { Separator } from "@/components/ui/separator"; import { Switch } from "@/components/ui/switch"; import { Tabs, TabsContent, TabsList, TabsTrigger } from "@/components/ui/tabs"; import { Textarea } from "@/components/ui/textarea"; import { useSettingsStore } from "../stores/settings-store"; const effectOptions = [ { value: "saturn", label: "Saturn" }, { value: "constellation", label: "Network (Constellation)" }, ]; const logServiceOptions = [ { value: "paste.rs", label: "paste.rs (Free, No Account)" }, { value: "pastebin.com", label: "pastebin.com (Requires API Key)" }, ]; const llmProviderOptions = [ { value: "ollama", label: "Ollama (Local)" }, { value: "openai", label: "OpenAI (Remote)" }, ]; const languageOptions = [ { value: "auto", label: "Auto (Match User)" }, { value: "English", label: "English" }, { value: "Chinese", label: "中文" }, { value: "Japanese", label: "日本語" }, { value: "Korean", label: "한국어" }, { value: "Spanish", label: "Español" }, { value: "French", label: "Français" }, { value: "German", label: "Deutsch" }, { value: "Russian", label: "Русский" }, ]; const ttsProviderOptions = [ { value: "disabled", label: "Disabled" }, { value: "piper", label: "Piper TTS (Local)" }, { value: "edge", label: "Edge TTS (Online)" }, ]; const personas = [ { value: "default", label: "Minecraft Expert (Default)", prompt: "You are a helpful Minecraft expert assistant. You help players with game issues, mod installation, performance optimization, and gameplay tips. Analyze any game logs provided and give concise, actionable advice.", }, { value: "technical", label: "Technical Debugger", prompt: "You are a technical support specialist for Minecraft. Focus strictly on analyzing logs, identifying crash causes, and providing technical solutions. Be precise and avoid conversational filler.", }, { value: "concise", label: "Concise Helper", prompt: "You are a direct and concise assistant. Provide answers in as few words as possible while remaining accurate. Use bullet points for lists.", }, { value: "explain", label: "Teacher / Explainer", prompt: "You are a patient teacher. Explain Minecraft concepts, redstone mechanics, and mod features in simple, easy-to-understand terms suitable for beginners.", }, { value: "pirate", label: "Pirate Captain", prompt: "You are a salty Minecraft Pirate Captain! Yarr! Speak like a pirate while helping the crew (the user) with their blocky adventures. Use terms like 'matey', 'landlubber', and 'treasure'.", }, ]; export function SettingsView() { const { settings, backgroundUrl, javaInstallations, isDetectingJava, showJavaDownloadModal, selectedDownloadSource, javaCatalog, isLoadingCatalog, catalogError, selectedMajorVersion, selectedImageType, showOnlyRecommended, searchQuery, isDownloadingJava, downloadProgress, javaDownloadStatus, pendingDownloads, ollamaModels, openaiModels, isLoadingOllamaModels, isLoadingOpenaiModels, ollamaModelsError, openaiModelsError, showConfigEditor, rawConfigContent, configFilePath, configEditorError, filteredReleases, availableMajorVersions, installStatus, selectedRelease, currentModelOptions, loadSettings, saveSettings, detectJava, selectJava, openJavaDownloadModal, closeJavaDownloadModal, loadJavaCatalog, refreshCatalog, loadPendingDownloads, selectMajorVersion, downloadJava, cancelDownload, resumeDownloads, openConfigEditor, closeConfigEditor, saveRawConfig, loadOllamaModels, loadOpenaiModels, set, setSetting, setAssistantSetting, setFeatureFlag, } = useSettingsStore(); // Mark potentially-unused variables as referenced so TypeScript does not report // them as unused in this file (they are part of the store API and used elsewhere). // This is a no-op but satisfies the compiler. void selectedDownloadSource; void javaCatalog; void javaDownloadStatus; void pendingDownloads; void ollamaModels; void openaiModels; void isLoadingOllamaModels; void isLoadingOpenaiModels; void ollamaModelsError; void openaiModelsError; void selectedRelease; void loadJavaCatalog; void loadPendingDownloads; void cancelDownload; void resumeDownloads; void setFeatureFlag; const [selectedPersona, setSelectedPersona] = useState("default"); const [migrating, setMigrating] = useState(false); const [activeTab, setActiveTab] = useState("appearance"); useEffect(() => { loadSettings(); detectJava(); }, [loadSettings, detectJava]); useEffect(() => { if (activeTab === "assistant") { if (settings.assistant.llmProvider === "ollama") { loadOllamaModels(); } else if (settings.assistant.llmProvider === "openai") { loadOpenaiModels(); } } }, [ activeTab, settings.assistant.llmProvider, loadOllamaModels, loadOpenaiModels, ]); const handleSelectBackground = async () => { try { const selected = await open({ multiple: false, filters: [ { name: "Images", extensions: ["png", "jpg", "jpeg", "webp", "gif"], }, ], }); if (selected && typeof selected === "string") { setSetting("customBackgroundPath", selected); saveSettings(); } } catch (e) { console.error("Failed to select background:", e); toast.error("Failed to select background"); } }; const handleClearBackground = () => { setSetting("customBackgroundPath", null); saveSettings(); }; const handleApplyPersona = (value: string) => { const persona = personas.find((p) => p.value === value); if (persona) { setAssistantSetting("systemPrompt", persona.prompt); setSelectedPersona(value); saveSettings(); } }; const handleResetSystemPrompt = () => { const defaultPersona = personas.find((p) => p.value === "default"); if (defaultPersona) { setAssistantSetting("systemPrompt", defaultPersona.prompt); setSelectedPersona("default"); saveSettings(); } }; const handleRunMigration = async () => { if (migrating) return; setMigrating(true); try { await new Promise((resolve) => setTimeout(resolve, 2000)); toast.success("Migration complete! Files migrated successfully"); } catch (e) { console.error("Migration failed:", e); toast.error(`Migration failed: ${e}`); } finally { setMigrating(false); } }; return (

Settings

Appearance Java Advanced Assistant Appearance
{backgroundUrl ? ( Background Preview { console.error("Failed to load image"); e.currentTarget.style.display = "none"; }} /> ) : (
)} {!backgroundUrl && (
Default Gradient
)}
{backgroundUrl && ( )}

Select an image from your computer to replace the default gradient background.

Enable particle effects and animated gradients.

{ setSetting("enableVisualEffects", checked); saveSettings(); }} />
{settings.enableVisualEffects && (

Select the active visual theme.

)}

Enable GPU acceleration for the interface.

{ setSetting("enableGpuAcceleration", checked); saveSettings(); }} />
Java Environment
setSetting("javaPath", e.target.value)} className="flex-1" placeholder="java or full path to java executable" />

Path to Java executable.

setSetting( "minMemory", parseInt(e.target.value, 10) || 1024, ) } min={512} step={256} />
setSetting( "maxMemory", parseInt(e.target.value, 10) || 2048, ) } min={1024} step={256} />

Memory allocation for Minecraft.

{javaInstallations.length === 0 ? (

No Java installations detected

) : (
{javaInstallations.map((installation) => ( selectJava(installation.path)} >
{installation.version}
{installation.path}
{settings.javaPath === installation.path && (
)}
))}
)}
Advanced Settings
setSetting( "downloadThreads", parseInt(e.target.value, 10) || 32, ) } min={1} max={64} />

Number of concurrent downloads.

{settings.logUploadService === "pastebin.com" && (
setSetting("pastebinApiKey", e.target.value || null) } placeholder="Enter your Pastebin API key" />
)}

Share downloaded assets between instances.

{ setSetting("useSharedCaches", checked); saveSettings(); }} />
{!settings.useSharedCaches && (

Maintain separate cache folders for compatibility.

{ setSetting("keepLegacyPerInstanceStorage", checked); saveSettings(); }} />
)} {settings.useSharedCaches && (
)}
AI Assistant

Enable the AI assistant for help with Minecraft issues.

{ setAssistantSetting("enabled", checked); saveSettings(); }} />
{settings.assistant.enabled && ( <>
{settings.assistant.llmProvider === "ollama" && (
{ setAssistantSetting( "ollamaEndpoint", e.target.value, ); saveSettings(); }} placeholder="http://localhost:11434" />
)} {settings.assistant.llmProvider === "openai" && ( <>
{ setAssistantSetting( "openaiApiKey", e.target.value || null, ); saveSettings(); }} placeholder="Enter your OpenAI API key" />
{ setAssistantSetting( "openaiEndpoint", e.target.value, ); saveSettings(); }} placeholder="https://api.openai.com/v1" />
)}