Spaces:
Running
Running
| <html lang="en"> | |
| <head> | |
| <meta charset="UTF-8"> | |
| <meta name="viewport" content="width=device-width, initial-scale=1.0"> | |
| <title>Autonomous AI Dev System</title> | |
| <link href="https://fonts.googleapis.com/css2?family=JetBrains+Mono:wght@300;400;500;600;700&family=Space+Grotesk:wght@300;400;500;600;700&display=swap" rel="stylesheet"> | |
| <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/6.5.1/css/all.min.css"> | |
| <style> | |
| :root { | |
| --bg-deep: #0a0e17; | |
| --bg-surface: #111827; | |
| --bg-card: #1a2234; | |
| --bg-card-hover: #1f2a40; | |
| --border: #2a3550; | |
| --border-active: #3b82f6; | |
| --fg: #e2e8f0; | |
| --fg-muted: #8892a8; | |
| --fg-dim: #4a5568; | |
| --accent-cyan: #06d6a0; | |
| --accent-teal: #0ea5e9; | |
| --accent-orange: #f59e0b; | |
| --accent-red: #ef4444; | |
| --accent-purple: #a855f7; | |
| --accent-pink: #ec4899; | |
| --accent-lime: #84cc16; | |
| --glow-cyan: rgba(6, 214, 160, 0.15); | |
| --glow-orange: rgba(245, 158, 11, 0.15); | |
| --glow-red: rgba(239, 68, 68, 0.15); | |
| --radius: 12px; | |
| --radius-sm: 8px; | |
| --radius-xs: 6px; | |
| --transition: 0.3s cubic-bezier(0.4, 0, 0.2, 1); | |
| --font-mono: 'JetBrains Mono', monospace; | |
| --font-sans: 'Space Grotesk', sans-serif; | |
| } | |
| *, *::before, *::after { box-sizing: border-box; margin: 0; padding: 0; } | |
| html { scroll-behavior: smooth; } | |
| body { | |
| font-family: var(--font-sans); | |
| background: var(--bg-deep); | |
| color: var(--fg); | |
| line-height: 1.6; | |
| min-height: 100vh; | |
| overflow-x: hidden; | |
| } | |
| /* Background atmosphere */ | |
| body::before { | |
| content: ''; | |
| position: fixed; | |
| top: 0; left: 0; right: 0; bottom: 0; | |
| background: | |
| radial-gradient(ellipse 800px 600px at 20% 10%, rgba(6, 214, 160, 0.04), transparent), | |
| radial-gradient(ellipse 600px 500px at 80% 80%, rgba(14, 165, 233, 0.04), transparent), | |
| radial-gradient(ellipse 400px 400px at 50% 50%, rgba(168, 85, 247, 0.02), transparent); | |
| pointer-events: none; | |
| z-index: 0; | |
| } | |
| /* Scrollbar */ | |
| ::-webkit-scrollbar { width: 6px; height: 6px; } | |
| ::-webkit-scrollbar-track { background: var(--bg-deep); } | |
| ::-webkit-scrollbar-thumb { background: var(--border); border-radius: 3px; } | |
| ::-webkit-scrollbar-thumb:hover { background: var(--fg-dim); } | |
| /* Layout */ | |
| .app-container { | |
| position: relative; | |
| z-index: 1; | |
| max-width: 1600px; | |
| margin: 0 auto; | |
| padding: 0 24px; | |
| } | |
| /* Header */ | |
| header { | |
| padding: 20px 0; | |
| display: flex; | |
| align-items: center; | |
| justify-content: space-between; | |
| flex-wrap: wrap; | |
| gap: 16px; | |
| border-bottom: 1px solid var(--border); | |
| margin-bottom: 24px; | |
| } | |
| .header-left { | |
| display: flex; | |
| align-items: center; | |
| gap: 16px; | |
| } | |
| .logo-icon { | |
| width: 44px; | |
| height: 44px; | |
| background: linear-gradient(135deg, var(--accent-cyan), var(--accent-teal)); | |
| border-radius: var(--radius-sm); | |
| display: flex; | |
| align-items: center; | |
| justify-content: center; | |
| font-size: 20px; | |
| color: var(--bg-deep); | |
| font-weight: 700; | |
| box-shadow: 0 0 20px rgba(6, 214, 160, 0.3); | |
| animation: logoPulse 3s ease-in-out infinite; | |
| } | |
| @keyframes logoPulse { | |
| 0%, 100% { box-shadow: 0 0 20px rgba(6, 214, 160, 0.3); } | |
| 50% { box-shadow: 0 0 30px rgba(6, 214, 160, 0.5); } | |
| } | |
| .header-title h1 { | |
| font-size: 1.3rem; | |
| font-weight: 700; | |
| letter-spacing: -0.02em; | |
| background: linear-gradient(135deg, var(--accent-cyan), var(--accent-teal)); | |
| -webkit-background-clip: text; | |
| -webkit-text-fill-color: transparent; | |
| background-clip: text; | |
| } | |
| .header-title p { | |
| font-size: 0.75rem; | |
| color: var(--fg-muted); | |
| font-weight: 400; | |
| } | |
| .built-with { | |
| font-size: 0.7rem; | |
| color: var(--fg-dim); | |
| text-decoration: none; | |
| padding: 4px 10px; | |
| border: 1px solid var(--border); | |
| border-radius: var(--radius-xs); | |
| transition: var(--transition); | |
| } | |
| .built-with:hover { | |
| color: var(--accent-cyan); | |
| border-color: var(--accent-cyan); | |
| background: var(--glow-cyan); | |
| } | |
| /* Mode selector */ | |
| .mode-selector { | |
| display: flex; | |
| gap: 4px; | |
| background: var(--bg-surface); | |
| padding: 4px; | |
| border-radius: var(--radius-sm); | |
| border: 1px solid var(--border); | |
| } | |
| .mode-btn { | |
| padding: 6px 14px; | |
| border: none; | |
| background: transparent; | |
| color: var(--fg-muted); | |
| font-family: var(--font-sans); | |
| font-size: 0.75rem; | |
| font-weight: 500; | |
| border-radius: var(--radius-xs); | |
| cursor: pointer; | |
| transition: var(--transition); | |
| display: flex; | |
| align-items: center; | |
| gap: 6px; | |
| } | |
| .mode-btn:hover { color: var(--fg); background: var(--bg-card); } | |
| .mode-btn.active { | |
| background: var(--accent-cyan); | |
| color: var(--bg-deep); | |
| font-weight: 600; | |
| } | |
| .mode-btn.active.mode-fast { background: var(--accent-orange); } | |
| .mode-btn.active.mode-debug { background: var(--accent-purple); } | |
| /* Status bar */ | |
| .status-bar { | |
| display: flex; | |
| gap: 16px; | |
| flex-wrap: wrap; | |
| margin-bottom: 24px; | |
| } | |
| .status-item { | |
| display: flex; | |
| align-items: center; | |
| gap: 8px; | |
| padding: 8px 14px; | |
| background: var(--bg-card); | |
| border: 1px solid var(--border); | |
| border-radius: var(--radius-sm); | |
| font-size: 0.78rem; | |
| transition: var(--transition); | |
| } | |
| .status-dot { | |
| width: 8px; | |
| height: 8px; | |
| border-radius: 50%; | |
| background: var(--accent-cyan); | |
| animation: dotBlink 2s ease-in-out infinite; | |
| } | |
| .status-dot.idle { background: var(--fg-dim); animation: none; } | |
| .status-dot.running { background: var(--accent-cyan); } | |
| .status-dot.error { background: var(--accent-red); animation: none; } | |
| @keyframes dotBlink { | |
| 0%, 100% { opacity: 1; } | |
| 50% { opacity: 0.4; } | |
| } | |
| .status-label { color: var(--fg-muted); } | |
| .status-value { color: var(--fg); font-weight: 600; } | |
| /* Main grid */ | |
| .main-grid { | |
| display: grid; | |
| grid-template-columns: 1fr 1fr; | |
| gap: 20px; | |
| margin-bottom: 24px; | |
| } | |
| /* Cards */ | |
| .card { | |
| background: var(--bg-card); | |
| border: 1px solid var(--border); | |
| border-radius: var(--radius); | |
| overflow: hidden; | |
| transition: var(--transition); | |
| } | |
| .card:hover { | |
| border-color: rgba(6, 214, 160, 0.2); | |
| box-shadow: 0 4px 24px rgba(0, 0, 0, 0.3); | |
| } | |
| .card-header { | |
| display: flex; | |
| align-items: center; | |
| justify-content: space-between; | |
| padding: 14px 18px; | |
| border-bottom: 1px solid var(--border); | |
| background: rgba(255, 255, 255, 0.01); | |
| } | |
| .card-header-left { | |
| display: flex; | |
| align-items: center; | |
| gap: 10px; | |
| } | |
| .card-icon { | |
| width: 32px; | |
| height: 32px; | |
| border-radius: var(--radius-xs); | |
| display: flex; | |
| align-items: center; | |
| justify-content: center; | |
| font-size: 14px; | |
| } | |
| .card-title { | |
| font-size: 0.85rem; | |
| font-weight: 600; | |
| letter-spacing: -0.01em; | |
| } | |
| .card-badge { | |
| font-size: 0.65rem; | |
| padding: 2px 8px; | |
| border-radius: 10px; | |
| font-weight: 600; | |
| text-transform: uppercase; | |
| letter-spacing: 0.05em; | |
| } | |
| .card-body { | |
| padding: 16px 18px; | |
| } | |
| /* Task input */ | |
| .task-input-section { | |
| grid-column: 1 / -1; | |
| } | |
| .task-input-wrapper { | |
| display: flex; | |
| gap: 12px; | |
| align-items: flex-end; | |
| } | |
| .input-group { | |
| flex: 1; | |
| display: flex; | |
| flex-direction: column; | |
| gap: 6px; | |
| } | |
| .input-group label { | |
| font-size: 0.72rem; | |
| color: var(--fg-muted); | |
| font-weight: 500; | |
| text-transform: uppercase; | |
| letter-spacing: 0.06em; | |
| } | |
| .task-textarea { | |
| width: 100%; | |
| min-height: 80px; | |
| padding: 12px 14px; | |
| background: var(--bg-surface); | |
| border: 1px solid var(--border); | |
| border-radius: var(--radius-sm); | |
| color: var(--fg); | |
| font-family: var(--font-sans); | |
| font-size: 0.85rem; | |
| resize: vertical; | |
| transition: var(--transition); | |
| line-height: 1.5; | |
| } | |
| .task-textarea:focus { | |
| outline: none; | |
| border-color: var(--accent-cyan); | |
| box-shadow: 0 0 0 3px var(--glow-cyan); | |
| } | |
| .task-textarea::placeholder { color: var(--fg-dim); } | |
| .btn-execute { | |
| padding: 12px 28px; | |
| background: linear-gradient(135deg, var(--accent-cyan), var(--accent-teal)); | |
| color: var(--bg-deep); | |
| border: none; | |
| border-radius: var(--radius-sm); | |
| font-family: var(--font-sans); | |
| font-size: 0.85rem; | |
| font-weight: 700; | |
| cursor: pointer; | |
| transition: var(--transition); | |
| white-space: nowrap; | |
| display: flex; | |
| align-items: center; | |
| gap: 8px; | |
| min-height: 48px; | |
| } | |
| .btn-execute:hover { | |
| transform: translateY(-1px); | |
| box-shadow: 0 6px 24px rgba(6, 214, 160, 0.3); | |
| } | |
| .btn-execute:active { transform: translateY(0); } | |
| .btn-execute:disabled { | |
| opacity: 0.5; | |
| cursor: not-allowed; | |
| transform: none; | |
| box-shadow: none; | |
| } | |
| .btn-secondary { | |
| padding: 8px 16px; | |
| background: var(--bg-surface); | |
| color: var(--fg-muted); | |
| border: 1px solid var(--border); | |
| border-radius: var(--radius-xs); | |
| font-family: var(--font-sans); | |
| font-size: 0.75rem; | |
| font-weight: 500; | |
| cursor: pointer; | |
| transition: var(--transition); | |
| } | |
| .btn-secondary:hover { | |
| color: var(--fg); | |
| border-color: var(--fg-dim); | |
| } | |
| /* Agent grid */ | |
| .agents-grid { | |
| display: grid; | |
| grid-template-columns: repeat(auto-fill, minmax(140px, 1fr)); | |
| gap: 10px; | |
| } | |
| .agent-card { | |
| background: var(--bg-surface); | |
| border: 1px solid var(--border); | |
| border-radius: var(--radius-sm); | |
| padding: 12px; | |
| cursor: pointer; | |
| transition: var(--transition); | |
| position: relative; | |
| overflow: hidden; | |
| } | |
| .agent-card::before { | |
| content: ''; | |
| position: absolute; | |
| top: 0; left: 0; right: 0; | |
| height: 2px; | |
| background: var(--agent-color, var(--fg-dim)); | |
| opacity: 0; | |
| transition: var(--transition); | |
| } | |
| .agent-card:hover::before, | |
| .agent-card.active::before { opacity: 1; } | |
| .agent-card:hover { | |
| border-color: var(--agent-color, var(--border-active)); | |
| transform: translateY(-2px); | |
| box-shadow: 0 4px 16px rgba(0, 0, 0, 0.3); | |
| } | |
| .agent-card.active { | |
| border-color: var(--agent-color, var(--accent-cyan)); | |
| background: rgba(255, 255, 255, 0.03); | |
| } | |
| .agent-card.working { | |
| animation: agentWorking 1.5s ease-in-out infinite; | |
| } | |
| @keyframes agentWorking { | |
| 0%, 100% { box-shadow: 0 0 0 0 var(--glow-cyan); } | |
| 50% { box-shadow: 0 0 16px 2px var(--glow-cyan); } | |
| } | |
| .agent-icon-wrap { | |
| width: 36px; | |
| height: 36px; | |
| border-radius: var(--radius-xs); | |
| display: flex; | |
| align-items: center; | |
| justify-content: center; | |
| font-size: 16px; | |
| margin-bottom: 8px; | |
| color: var(--agent-color, var(--fg-muted)); | |
| background: rgba(255, 255, 255, 0.04); | |
| } | |
| .agent-name { | |
| font-size: 0.72rem; | |
| font-weight: 600; | |
| margin-bottom: 2px; | |
| color: var(--fg); | |
| } | |
| .agent-role { | |
| font-size: 0.62rem; | |
| color: var(--fg-muted); | |
| line-height: 1.3; | |
| } | |
| .agent-status-dot { | |
| position: absolute; | |
| top: 8px; | |
| right: 8px; | |
| width: 6px; | |
| height: 6px; | |
| border-radius: 50%; | |
| background: var(--fg-dim); | |
| } | |
| .agent-status-dot.active { background: var(--accent-cyan); animation: dotBlink 1s ease-in-out infinite; } | |
| .agent-status-dot.done { background: var(--accent-lime); animation: none; } | |
| .agent-status-dot.error { background: var(--accent-red); animation: none; } | |
| /* Workflow pipeline */ | |
| .workflow-pipeline { | |
| display: flex; | |
| flex-direction: column; | |
| gap: 0; | |
| } | |
| .workflow-step { | |
| display: flex; | |
| align-items: flex-start; | |
| gap: 14px; | |
| padding: 12px 0; | |
| position: relative; | |
| } | |
| .workflow-step:not(:last-child)::after { | |
| content: ''; | |
| position: absolute; | |
| left: 15px; | |
| top: 40px; | |
| bottom: -4px; | |
| width: 2px; | |
| background: var(--border); | |
| } | |
| .workflow-step.active:not(:last-child)::after { | |
| background: var(--accent-cyan); | |
| box-shadow: 0 0 8px var(--glow-cyan); | |
| } | |
| .workflow-step.completed:not(:last-child)::after { | |
| background: var(--accent-lime); | |
| } | |
| .step-indicator { | |
| width: 32px; | |
| height: 32px; | |
| border-radius: 50%; | |
| display: flex; | |
| align-items: center; | |
| justify-content: center; | |
| font-size: 12px; | |
| font-weight: 700; | |
| background: var(--bg-surface); | |
| border: 2px solid var(--border); | |
| color: var(--fg-dim); | |
| flex-shrink: 0; | |
| transition: var(--transition); | |
| z-index: 1; | |
| } | |
| .workflow-step.active .step-indicator { | |
| border-color: var(--accent-cyan); | |
| color: var(--accent-cyan); | |
| background: var(--glow-cyan); | |
| animation: stepPulse 2s ease-in-out infinite; | |
| } | |
| .workflow-step.completed .step-indicator { | |
| border-color: var(--accent-lime); | |
| color: var(--bg-deep); | |
| background: var(--accent-lime); | |
| } | |
| .workflow-step.failed .step-indicator { | |
| border-color: var(--accent-red); | |
| color: var(--accent-red); | |
| background: var(--glow-red); | |
| } | |
| @keyframes stepPulse { | |
| 0%, 100% { box-shadow: 0 0 0 0 var(--glow-cyan); } | |
| 50% { box-shadow: 0 0 12px 4px var(--glow-cyan); } | |
| } | |
| .step-content { | |
| flex: 1; | |
| min-width: 0; | |
| } | |
| .step-title { | |
| font-size: 0.8rem; | |
| font-weight: 600; | |
| color: var(--fg); | |
| margin-bottom: 2px; | |
| } | |
| .step-desc { | |
| font-size: 0.7rem; | |
| color: var(--fg-muted); | |
| } | |
| .step-detail { | |
| margin-top: 8px; | |
| padding: 10px 12px; | |
| background: var(--bg-surface); | |
| border: 1px solid var(--border); | |
| border-radius: var(--radius-xs); | |
| font-family: var(--font-mono); | |
| font-size: 0.68rem; | |
| color: var(--fg-muted); | |
| line-height: 1.6; | |
| max-height: 200px; | |
| overflow-y: auto; | |
| display: none; | |
| } | |
| .workflow-step.active .step-detail, | |
| .workflow-step.completed .step-detail { | |
| display: block; | |
| } | |
| /* Execution log */ | |
| .log-container { | |
| max-height: 400px; | |
| overflow-y: auto; | |
| display: flex; | |
| flex-direction: column; | |
| gap: 4px; | |
| } | |
| .log-entry { | |
| display: flex; | |
| align-items: flex-start; | |
| gap: 10px; | |
| padding: 8px 10px; | |
| background: var(--bg-surface); | |
| border-radius: var(--radius-xs); | |
| font-size: 0.72rem; | |
| animation: logSlideIn 0.3s ease-out; | |
| border-left: 3px solid transparent; | |
| } | |
| .log-entry.info { border-left-color: var(--accent-teal); } | |
| .log-entry.success { border-left-color: var(--accent-lime); } | |
| .log-entry.warning { border-left-color: var(--accent-orange); } | |
| .log-entry.error { border-left-color: var(--accent-red); } | |
| .log-entry.agent { border-left-color: var(--accent-purple); } | |
| @keyframes logSlideIn { | |
| from { opacity: 0; transform: translateX(-8px); } | |
| to { opacity: 1; transform: translateX(0); } | |
| } | |
| .log-time { | |
| color: var(--fg-dim); | |
| font-family: var(--font-mono); | |
| font-size: 0.65rem; | |
| white-space: nowrap; | |
| padding-top: 1px; | |
| } | |
| .log-agent { | |
| color: var(--accent-cyan); | |
| font-weight: 600; | |
| white-space: nowrap; | |
| } | |
| .log-msg { | |
| color: var(--fg-muted); | |
| flex: 1; | |
| min-width: 0; | |
| word-break: break-word; | |
| } | |
| /* Knowledge base */ | |
| .kb-list { | |
| display: flex; | |
| flex-direction: column; | |
| gap: 8px; | |
| max-height: 350px; | |
| overflow-y: auto; | |
| } | |
| .kb-entry { | |
| padding: 10px 12px; | |
| background: var(--bg-surface); | |
| border: 1px solid var(--border); | |
| border-radius: var(--radius-xs); | |
| transition: var(--transition); | |
| } | |
| .kb-entry:hover { | |
| border-color: rgba(168, 85, 247, 0.3); | |
| } | |
| .kb-rule { | |
| font-family: var(--font-mono); | |
| font-size: 0.68rem; | |
| color: var(--accent-purple); | |
| margin-bottom: 4px; | |
| } | |
| .kb-meta { | |
| display: flex; | |
| gap: 12px; | |
| font-size: 0.62rem; | |
| color: var(--fg-dim); | |
| } | |
| .kb-score { | |
| color: var(--accent-lime); | |
| font-weight: 600; | |
| } | |
| /* JSON viewer */ | |
| .json-viewer { | |
| font-family: var(--font-mono); | |
| font-size: 0.7rem; | |
| line-height: 1.6; | |
| color: var(--fg-muted); | |
| max-height: 300px; | |
| overflow-y: auto; | |
| padding: 12px; | |
| background: var(--bg-surface); | |
| border-radius: var(--radius-xs); | |
| border: 1px solid var(--border); | |
| white-space: pre-wrap; | |
| word-break: break-all; | |
| } | |
| .json-key { color: var(--accent-cyan); } | |
| .json-string { color: var(--accent-orange); } | |
| .json-number { color: var(--accent-purple); } | |
| .json-bool { color: var(--accent-pink); } | |
| .json-null { color: var(--fg-dim); } | |
| /* Definition of Done */ | |
| .dod-list { | |
| display: flex; | |
| flex-direction: column; | |
| gap: 6px; | |
| } | |
| .dod-item { | |
| display: flex; | |
| align-items: center; | |
| gap: 10px; | |
| padding: 8px 12px; | |
| background: var(--bg-surface); | |
| border-radius: var(--radius-xs); | |
| font-size: 0.78rem; | |
| transition: var(--transition); | |
| } | |
| .dod-check { | |
| width: 20px; | |
| height: 20px; | |
| border-radius: 50%; | |
| display: flex; | |
| align-items: center; | |
| justify-content: center; | |
| font-size: 10px; | |
| border: 2px solid var(--border); | |
| color: transparent; | |
| transition: var(--transition); | |
| flex-shrink: 0; | |
| } | |
| .dod-item.checked .dod-check { | |
| border-color: var(--accent-lime); | |
| background: var(--accent-lime); | |
| color: var(--bg-deep); | |
| } | |
| .dod-item.checked { | |
| color: var(--fg-muted); | |
| } | |
| .dod-item.checked .dod-text { | |
| text-decoration: line-through; | |
| } | |
| .dod-text { color: var(--fg); } | |
| /* Task decomposition */ | |
| .task-tree { | |
| display: flex; | |
| flex-direction: column; | |
| gap: 6px; | |
| } | |
| .task-node { | |
| display: flex; | |
| align-items: center; | |
| gap: 10px; | |
| padding: 8px 12px; | |
| background: var(--bg-surface); | |
| border: 1px solid var(--border); | |
| border-radius: var(--radius-xs); | |
| font-size: 0.75rem; | |
| transition: var(--transition); | |
| animation: taskAppear 0.4s ease-out; | |
| } | |
| @keyframes taskAppear { | |
| from { opacity: 0; transform: translateY(-8px); } | |
| to { opacity: 1; transform: translateY(0); } | |
| } | |
| .task-node:hover { border-color: var(--accent-teal); } | |
| .task-status-icon { | |
| font-size: 10px; | |
| width: 20px; | |
| height: 20px; | |
| display: flex; | |
| align-items: center; | |
| justify-content: center; | |
| border-radius: 50%; | |
| flex-shrink: 0; | |
| } | |
| .task-status-icon.pending { color: var(--fg-dim); } | |
| .task-status-icon.in-progress { color: var(--accent-orange); animation: dotBlink 1s ease-in-out infinite; } | |
| .task-status-icon.done { color: var(--accent-lime); } | |
| .task-status-icon.failed { color: var(--accent-red); } | |
| .task-agent-tag { | |
| font-size: 0.62rem; | |
| padding: 2px 8px; | |
| border-radius: 10px; | |
| background: rgba(6, 214, 160, 0.1); | |
| color: var(--accent-cyan); | |
| font-weight: 600; | |
| white-space: nowrap; | |
| } | |
| .task-desc { | |
| flex: 1; | |
| color: var(--fg); | |
| min-width: 0; | |
| overflow: hidden; | |
| text-overflow: ellipsis; | |
| white-space: nowrap; | |
| } | |
| /* Communication feed */ | |
| .comm-feed { | |
| display: flex; | |
| flex-direction: column; | |
| gap: 8px; | |
| max-height: 350px; | |
| overflow-y: auto; | |
| } | |
| .comm-msg { | |
| padding: 10px 12px; | |
| background: var(--bg-surface); | |
| border: 1px solid var(--border); | |
| border-radius: var(--radius-xs); | |
| animation: logSlideIn 0.3s ease-out; | |
| } | |
| .comm-msg-header { | |
| display: flex; | |
| align-items: center; | |
| justify-content: space-between; | |
| margin-bottom: 6px; | |
| } | |
| .comm-from { | |
| font-size: 0.72rem; | |
| font-weight: 600; | |
| color: var(--accent-cyan); | |
| } | |
| .comm-status { | |
| font-size: 0.6rem; | |
| padding: 2px 6px; | |
| border-radius: 8px; | |
| font-weight: 600; | |
| text-transform: uppercase; | |
| } | |
| .comm-status.done { background: rgba(132, 204, 22, 0.15); color: var(--accent-lime); } | |
| .comm-status.in_progress { background: rgba(245, 158, 11, 0.15); color: var(--accent-orange); } | |
| .comm-status.pending { background: rgba(74, 85, 104, 0.3); color: var(--fg-dim); } | |
| .comm-status.failed { background: rgba(239, 68, 68, 0.15); color: var(--accent-red); } | |
| .comm-body { | |
| font-size: 0.7rem; | |
| color: var(--fg-muted); | |
| font-family: var(--font-mono); | |
| line-height: 1.5; | |
| } | |
| /* Full-width sections */ | |
| .full-width { | |
| grid-column: 1 / -1; | |
| } | |
| /* Tab system */ | |
| .tabs { | |
| display: flex; | |
| gap: 2px; | |
| background: var(--bg-surface); | |
| padding: 3px; | |
| border-radius: var(--radius-xs); | |
| } | |
| .tab-btn { | |
| padding: 5px 12px; | |
| border: none; | |
| background: transparent; | |
| color: var(--fg-muted); | |
| font-family: var(--font-sans); | |
| font-size: 0.7rem; | |
| font-weight: 500; | |
| border-radius: var(--radius-xs); | |
| cursor: pointer; | |
| transition: var(--transition); | |
| } | |
| .tab-btn:hover { color: var(--fg); } | |
| .tab-btn.active { background: var(--bg-card); color: var(--fg); font-weight: 600; } | |
| .tab-content { display: none; } | |
| .tab-content.active { display: block; } | |
| /* Progress bar */ | |
| .progress-bar { | |
| width: 100%; | |
| height: 4px; | |
| background: var(--bg-surface); | |
| border-radius: 2px; | |
| overflow: hidden; | |
| margin-top: 8px; | |
| } | |
| .progress-fill { | |
| height: 100%; | |
| background: linear-gradient(90deg, var(--accent-cyan), var(--accent-teal)); | |
| border-radius: 2px; | |
| transition: width 0.5s ease; | |
| width: 0%; | |
| } | |
| /* Notification toast */ | |
| .toast-container { | |
| position: fixed; | |
| top: 20px; | |
| right: 20px; | |
| z-index: 1000; | |
| display: flex; | |
| flex-direction: column; | |
| gap: 8px; | |
| } | |
| .toast { | |
| padding: 12px 18px; | |
| border-radius: var(--radius-sm); | |
| font-size: 0.78rem; | |
| font-weight: 500; | |
| animation: toastIn 0.4s ease-out, toastOut 0.4s ease-in 2.6s forwards; | |
| display: flex; | |
| align-items: center; | |
| gap: 8px; | |
| box-shadow: 0 8px 32px rgba(0, 0, 0, 0.4); | |
| } | |
| .toast.success { background: var(--accent-lime); color: var(--bg-deep); } | |
| .toast.error { background: var(--accent-red); color: #fff; } | |
| .toast.info { background: var(--accent-teal); color: var(--bg-deep); } | |
| .toast.warning { background: var(--accent-orange); color: var(--bg-deep); } | |
| @keyframes toastIn { | |
| from { opacity: 0; transform: translateX(40px); } | |
| to { opacity: 1; transform: translateX(0); } | |
| } | |
| @keyframes toastOut { | |
| from { opacity: 1; transform: translateX(0); } | |
| to { opacity: 0; transform: translateX(40px); } | |
| } | |
| /* Empty state */ | |
| .empty-state { | |
| text-align: center; | |
| padding: 30px 20px; | |
| color: var(--fg-dim); | |
| } | |
| .empty-state i { | |
| font-size: 28px; | |
| margin-bottom: 10px; | |
| display: block; | |
| opacity: 0.5; | |
| } | |
| .empty-state p { | |
| font-size: 0.78rem; | |
| } | |
| /* Responsive */ | |
| @media (max-width: 1024px) { | |
| .main-grid { | |
| grid-template-columns: 1fr; | |
| } | |
| } | |
| @media (max-width: 768px) { | |
| .app-container { padding: 0 12px; } | |
| header { padding: 14px 0; } | |
| .header-title h1 { font-size: 1.1rem; } | |
| .agents-grid { grid-template-columns: repeat(auto-fill, minmax(120px, 1fr)); } | |
| .task-input-wrapper { flex-direction: column; } | |
| .btn-execute { width: 100%; justify-content: center; } | |
| .status-bar { gap: 8px; } | |
| .status-item { padding: 6px 10px; font-size: 0.72rem; } | |
| } | |
| @media (max-width: 480px) { | |
| .agents-grid { grid-template-columns: repeat(2, 1fr); } | |
| .mode-selector { flex-wrap: wrap; } | |
| } | |
| /* Reduced motion */ | |
| @media (prefers-reduced-motion: reduce) { | |
| *, *::before, *::after { | |
| animation-duration: 0.01ms ; | |
| transition-duration: 0.01ms ; | |
| } | |
| } | |
| /* Particle canvas */ | |
| #particle-canvas { | |
| position: fixed; | |
| top: 0; left: 0; | |
| width: 100%; | |
| height: 100%; | |
| pointer-events: none; | |
| z-index: 0; | |
| opacity: 0.4; | |
| } | |
| </style> | |
| </head> | |
| <body> | |
| <canvas id="particle-canvas" aria-hidden="true"></canvas> | |
| <div class="toast-container" id="toastContainer"></div> | |
| <div class="app-container"> | |
| <header> | |
| <div class="header-left"> | |
| <div class="logo-icon"><i class="fas fa-brain"></i></div> | |
| <div class="header-title"> | |
| <h1>Autonomous AI Dev System</h1> | |
| <p>Self-organizing multi-agent engineering pipeline</p> | |
| </div> | |
| </div> | |
| <div style="display:flex;align-items:center;gap:12px;flex-wrap:wrap;"> | |
| <a href="https://huggingface.co/spaces/akhaliq/anycoder" target="_blank" class="built-with" rel="noopener">Built with anycoder</a> | |
| <div class="mode-selector"> | |
| <button class="mode-btn active" data-mode="safe" onclick="setMode('safe')"> | |
| <i class="fas fa-shield-halved"></i> Safe | |
| </button> | |
| <button class="mode-btn mode-fast" data-mode="fast" onclick="setMode('fast')"> | |
| <i class="fas fa-bolt"></i> Fast | |
| </button> | |
| <button class="mode-btn mode-debug" data-mode="debug" onclick="setMode('debug')"> | |
| <i class="fas fa-bug"></i> Debug | |
| </button> | |
| </div> | |
| </div> | |
| </header> | |
| <!-- Status bar --> | |
| <div class="status-bar"> | |
| <div class="status-item"> | |
| <div class="status-dot idle" id="systemDot"></div> | |
| <span class="status-label">System</span> | |
| <span class="status-value" id="systemStatus">Idle</span> | |
| </div> | |
| <div class="status-item"> | |
| <i class="fas fa-layer-group" style="color:var(--accent-teal);font-size:12px;"></i> | |
| <span class="status-label">Agents</span> | |
| <span class="status-value">11</span> | |
| </div> | |
| <div class="status-item"> | |
| <i class="fas fa-list-check" style="color:var(--accent-orange);font-size:12px;"></i> | |
| <span class="status-label">Tasks</span> | |
| <span class="status-value" id="taskCount">0</span> | |
| </div> | |
| <div class="status-item"> | |
| <i class="fas fa-book" style="color:var(--accent-purple);font-size:12px;"></i> | |
| <span class="status-label">Knowledge</span> | |
| <span class="status-value" id="kbCount">3</span> | |
| </div> | |
| <div class="status-item"> | |
| <i class="fas fa-clock" style="color:var(--accent-lime);font-size:12px;"></i> | |
| <span class="status-label">Elapsed</span> | |
| <span class="status-value" id="elapsedTime">0s</span> | |
| </div> | |
| <div class="status-item" style="margin-left:auto;"> | |
| <div class="progress-bar" style="width:120px;"> | |
| <div class="progress-fill" id="progressFill"></div> | |
| </div> | |
| <span class="status-value" id="progressPct">0%</span> | |
| </div> | |
| </div> | |
| <div class="main-grid"> | |
| <!-- Task Input --> | |
| <section class="card task-input-section" aria-label="Task Input"> | |
| <div class="card-header"> | |
| <div class="card-header-left"> | |
| <div class="card-icon" style="background:var(--glow-cyan);color:var(--accent-cyan);"> | |
| <i class="fas fa-terminal"></i> | |
| </div> | |
| <span class="card-title">Task Input</span> | |
| </div> | |
| <span class="card-badge" style="background:var(--glow-cyan);color:var(--accent-cyan);">Ready</span> | |
| </div> | |
| <div class="card-body"> | |
| <div class="task-input-wrapper"> | |
| <div class="input-group" style="flex:1;"> | |
| <label for="taskInput">Describe your software task</label> | |
| <textarea id="taskInput" class="task-textarea" placeholder="Example: Build a REST API for a task management app with user authentication, CRUD operations for tasks, and real-time notifications..."></textarea> | |
| </div> | |
| <div style="display:flex;flex-direction:column;gap:8px;"> | |
| <button class="btn-execute" id="executeBtn" onclick="startExecution()"> | |
| <i class="fas fa-play"></i> Execute | |
| </button> | |
| <button class="btn-secondary" onclick="resetSystem()"> | |
| <i class="fas fa-rotate-right"></i> Reset | |
| </button> | |
| </div> | |
| </div> | |
| </div> | |
| </section> | |
| <!-- Agent Grid --> | |
| <section class="card full-width" aria-label="Agent Team"> | |
| <div class="card-header"> | |
| <div class="card-header-left"> | |
| <div class="card-icon" style="background:rgba(168,85,247,0.15);color:var(--accent-purple);"> | |
| <i class="fas fa-users-gear"></i> | |
| </div> | |
| <span class="card-title">Agent Team</span> | |
| </div> | |
| <span class="card-badge" style="background:rgba(168,85,247,0.15);color:var(--accent-purple);">11 Agents</span> | |
| </div> | |
| <div class="card-body"> | |
| <div class="agents-grid" id="agentsGrid"></div> | |
| </div> | |
| </section> | |
| <!-- Workflow Pipeline --> | |
| <section class="card" aria-label="Workflow Pipeline"> | |
| <div class="card-header"> | |
| <div class="card-header-left"> | |
| <div class="card-icon" style="background:rgba(14,165,233,0.15);color:var(--accent-teal);"> | |
| <i class="fas fa-diagram-project"></i> | |
| </div> | |
| <span class="card-title">Workflow Pipeline</span> | |
| </div> | |
| </div> | |
| <div class="card-body"> | |
| <div class="workflow-pipeline" id="workflowPipeline"></div> | |
| </div> | |
| </section> | |
| <!-- Task Decomposition --> | |
| <section class="card" aria-label="Task Decomposition"> | |
| <div class="card-header"> | |
| <div class="card-header-left"> | |
| <div class="card-icon" style="background:var(--glow-orange);color:var(--accent-orange);"> | |
| <i class="fas fa-sitemap"></i> | |
| </div> | |
| <span class="card-title">Task Decomposition</span> | |
| </div> | |
| <div class="tabs"> | |
| <button class="tab-btn active" onclick="switchTab(this, 'tasksTab')">Tasks</button> | |
| <button class="tab-btn" onclick="switchTab(this, 'commTab')">Comm</button> | |
| </div> | |
| </div> | |
| <div class="card-body"> | |
| <div id="tasksTab" class="tab-content active"> | |
| <div class="task-tree" id="taskTree"> | |
| <div class="empty-state"> | |
| <i class="fas fa-puzzle-piece"></i> | |
| <p>Submit a task to see decomposition</p> | |
| </div> | |
| </div> | |
| </div> | |
| <div id="commTab" class="tab-content"> | |
| <div class="comm-feed" id="commFeed"> | |
| <div class="empty-state"> | |
| <i class="fas fa-comments"></i> | |
| <p>Agent communications will appear here</p> | |
| </div> | |
| </div> | |
| </div> | |
| </div> | |
| </section> | |
| <!-- Execution Log --> | |
| <section class="card" aria-label="Execution Log"> | |
| <div class="card-header"> | |
| <div class="card-header-left"> | |
| <div class="card-icon" style="background:rgba(132,204,22,0.15);color:var(--accent-lime);"> | |
| <i class="fas fa-scroll"></i> | |
| </div> | |
| <span class="card-title">Execution Log</span> | |
| </div> | |
| <button class="btn-secondary" onclick="clearLog()"> | |
| <i class="fas fa-trash-can"></i> Clear | |
| </button> | |
| </div> | |
| <div class="card-body"> | |
| <div class="log-container" id="logContainer"> | |
| <div class="empty-state"> | |
| <i class="fas fa-file-lines"></i> | |
| <p>Logs will appear during execution</p> | |
| </div> | |
| </div> | |
| </div> | |
| </section> | |
| <!-- Knowledge Base & JSON & DoD --> | |
| <section class="card" aria-label="Knowledge & Validation"> | |
| <div class="card-header"> | |
| <div class="card-header-left"> | |
| <div class="card-icon" style="background:rgba(168,85,247,0.15);color:var(--accent-purple);"> | |
| <i class="fas fa-brain"></i> | |
| </div> | |
| <span class="card-title">Knowledge & Validation</span> | |
| </div> | |
| <div class="tabs"> | |
| <button class="tab-btn active" onclick="switchTab(this, 'kbTab')">Knowledge</button> | |
| <button class="tab-btn" onclick="switchTab(this, 'jsonTab')">JSON</button> | |
| <button class="tab-btn" onclick="switchTab(this, 'dodTab')">DoD</button> | |
| </div> | |
| </div> | |
| <div class="card-body"> | |
| <div id="kbTab" class="tab-content active"> | |
| <div class="kb-list" id="kbList"></div> | |
| </div> | |
| <div id="jsonTab" class="tab-content"> | |
| <div class="json-viewer" id="jsonViewer">{ | |
| "message": "Submit a task to see agent communication JSON" | |
| }</div> | |
| </div> | |
| <div id="dodTab" class="tab-content"> | |
| <div class="dod-list" id="dodList"></div> | |
| </div> | |
| </div> | |
| </section> | |
| </div> | |
| </div> | |
| <script> | |
| // ======================================== | |
| // Agent definitions | |
| // ======================================== | |
| const AGENTS = [ | |
| { id: 'pm', name: 'Product Manager', icon: 'fa-clipboard-list', color: '#06d6a0', role: 'Requirements & priorities' }, | |
| { id: 'arch', name: 'Architect', icon: 'fa-drafting-compass', color: '#0ea5e9', role: 'System design & APIs' }, | |
| { id: 'planner', name: 'Task Planner', icon: 'fa-list-ol', color: '#a855f7', role: 'Task decomposition' }, | |
| { id: 'backend', name: 'Backend Dev', icon: 'fa-server', color: '#f59e0b', role: 'Server logic & APIs' }, | |
| { id: 'frontend', name: 'Frontend Dev', icon: |