infinite-agents-public/claude_code_devtools/claude_devtool_4.html

783 lines
28 KiB
HTML

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Dashboard Layout Tool - Claude Code DevTools</title>
<style>
/* CSS Reset & Base */
* {
margin: 0;
padding: 0;
box-sizing: border-box;
}
:root {
--bg-primary: #0d1117;
--bg-secondary: #161b22;
--bg-tertiary: #21262d;
--border-color: #30363d;
--text-primary: #c9d1d9;
--text-secondary: #8b949e;
--accent-blue: #58a6ff;
--accent-green: #3fb950;
--accent-yellow: #d29922;
--accent-purple: #bc8cff;
--accent-red: #f85149;
--shadow: rgba(0, 0, 0, 0.3);
}
body {
font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', 'Noto Sans', Helvetica, Arial, sans-serif;
background: var(--bg-primary);
color: var(--text-primary);
line-height: 1.6;
overflow-x: hidden;
}
/* Header */
header {
background: var(--bg-secondary);
border-bottom: 1px solid var(--border-color);
padding: 1.5rem 2rem;
position: sticky;
top: 0;
z-index: 100;
box-shadow: 0 2px 8px var(--shadow);
}
header h1 {
font-size: 1.5rem;
font-weight: 600;
color: var(--accent-blue);
margin-bottom: 0.25rem;
}
header .tagline {
color: var(--text-secondary);
font-size: 0.875rem;
}
/* Main Grid Dashboard Layout */
/* Technique 1: grid-template-areas for named layout regions */
main {
display: grid;
grid-template-areas:
"stats stats timeline timeline"
"usage usage activity activity"
"performance performance activity activity"
"docs docs docs docs";
grid-template-columns: repeat(4, 1fr);
grid-template-rows: auto auto auto auto;
gap: 1.5rem;
padding: 2rem;
max-width: 1600px;
margin: 0 auto;
}
/* Grid Area Assignments */
.stats-panel {
grid-area: stats;
}
.timeline-panel {
grid-area: timeline;
}
.usage-panel {
grid-area: usage;
}
.activity-panel {
grid-area: activity;
}
.performance-panel {
grid-area: performance;
}
.docs {
grid-area: docs;
}
/* Panel Styling */
.panel {
background: var(--bg-secondary);
border: 1px solid var(--border-color);
border-radius: 6px;
padding: 1.5rem;
box-shadow: 0 1px 3px var(--shadow);
transition: transform 0.2s, box-shadow 0.2s;
}
.panel:hover {
transform: translateY(-2px);
box-shadow: 0 4px 12px var(--shadow);
}
.panel h2 {
font-size: 1.125rem;
font-weight: 600;
margin-bottom: 1rem;
color: var(--accent-blue);
display: flex;
align-items: center;
gap: 0.5rem;
}
.panel-icon {
font-size: 1.25rem;
}
/* Stats Grid - Technique 2: auto-fit with minmax for responsive cards */
.stats-grid {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(120px, 1fr));
gap: 1rem;
}
.stat-card {
background: var(--bg-tertiary);
padding: 1rem;
border-radius: 4px;
border: 1px solid var(--border-color);
text-align: center;
}
.stat-value {
font-size: 1.75rem;
font-weight: 700;
display: block;
margin-bottom: 0.25rem;
}
.stat-label {
font-size: 0.75rem;
color: var(--text-secondary);
text-transform: uppercase;
letter-spacing: 0.5px;
}
.stat-card.blue .stat-value { color: var(--accent-blue); }
.stat-card.green .stat-value { color: var(--accent-green); }
.stat-card.yellow .stat-value { color: var(--accent-yellow); }
.stat-card.purple .stat-value { color: var(--accent-purple); }
/* Timeline */
.timeline {
position: relative;
}
.timeline-item {
display: flex;
gap: 0.75rem;
margin-bottom: 1rem;
padding-bottom: 1rem;
border-bottom: 1px solid var(--border-color);
}
.timeline-item:last-child {
border-bottom: none;
}
.timeline-time {
font-size: 0.75rem;
color: var(--text-secondary);
min-width: 60px;
font-family: 'SF Mono', Monaco, 'Cascadia Code', monospace;
}
.timeline-content {
flex: 1;
}
.timeline-title {
font-weight: 500;
margin-bottom: 0.25rem;
}
.timeline-desc {
font-size: 0.875rem;
color: var(--text-secondary);
}
.timeline-badge {
display: inline-block;
padding: 0.125rem 0.5rem;
border-radius: 3px;
font-size: 0.7rem;
font-weight: 500;
margin-left: 0.5rem;
}
.timeline-badge.edit { background: var(--accent-blue); color: #000; }
.timeline-badge.read { background: var(--accent-green); color: #000; }
.timeline-badge.bash { background: var(--accent-yellow); color: #000; }
.timeline-badge.search { background: var(--accent-purple); color: #000; }
/* Tool Usage Chart */
.usage-bars {
display: flex;
flex-direction: column;
gap: 0.75rem;
}
.usage-bar {
display: flex;
align-items: center;
gap: 1rem;
}
.usage-label {
min-width: 80px;
font-size: 0.875rem;
font-family: 'SF Mono', Monaco, 'Cascadia Code', monospace;
}
.usage-bar-bg {
flex: 1;
height: 24px;
background: var(--bg-tertiary);
border-radius: 4px;
overflow: hidden;
position: relative;
}
.usage-bar-fill {
height: 100%;
background: linear-gradient(90deg, var(--accent-blue), var(--accent-purple));
transition: width 1s ease;
display: flex;
align-items: center;
justify-content: flex-end;
padding-right: 0.5rem;
font-size: 0.75rem;
font-weight: 600;
}
/* Activity Feed */
.activity-feed {
max-height: 400px;
overflow-y: auto;
padding-right: 0.5rem;
}
.activity-feed::-webkit-scrollbar {
width: 8px;
}
.activity-feed::-webkit-scrollbar-track {
background: var(--bg-tertiary);
border-radius: 4px;
}
.activity-feed::-webkit-scrollbar-thumb {
background: var(--border-color);
border-radius: 4px;
}
.activity-item {
display: flex;
gap: 0.75rem;
margin-bottom: 1rem;
padding: 0.75rem;
background: var(--bg-tertiary);
border-radius: 4px;
border-left: 3px solid var(--accent-blue);
}
.activity-item.success { border-left-color: var(--accent-green); }
.activity-item.warning { border-left-color: var(--accent-yellow); }
.activity-item.error { border-left-color: var(--accent-red); }
.activity-icon {
font-size: 1.25rem;
opacity: 0.8;
}
.activity-content {
flex: 1;
}
.activity-title {
font-weight: 500;
margin-bottom: 0.25rem;
font-size: 0.875rem;
}
.activity-meta {
font-size: 0.75rem;
color: var(--text-secondary);
}
/* Performance Metrics Grid */
.performance-grid {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(150px, 1fr));
gap: 1rem;
}
.metric-card {
background: var(--bg-tertiary);
padding: 1rem;
border-radius: 4px;
border: 1px solid var(--border-color);
}
.metric-title {
font-size: 0.75rem;
color: var(--text-secondary);
text-transform: uppercase;
margin-bottom: 0.5rem;
}
.metric-value {
font-size: 1.5rem;
font-weight: 700;
color: var(--accent-green);
font-family: 'SF Mono', Monaco, 'Cascadia Code', monospace;
}
.metric-bar {
height: 4px;
background: var(--bg-primary);
border-radius: 2px;
margin-top: 0.5rem;
overflow: hidden;
}
.metric-bar-fill {
height: 100%;
background: var(--accent-green);
transition: width 1s ease;
}
/* Documentation Section */
.docs {
background: var(--bg-secondary);
border: 1px solid var(--border-color);
border-radius: 6px;
padding: 2rem;
}
.docs h2 {
font-size: 1.25rem;
margin-bottom: 1.5rem;
color: var(--accent-blue);
}
.doc-content h3 {
font-size: 1rem;
margin-top: 1.5rem;
margin-bottom: 0.75rem;
color: var(--accent-green);
}
.doc-content h3:first-child {
margin-top: 0;
}
.doc-content p {
margin-bottom: 1rem;
color: var(--text-secondary);
}
.doc-content ul, .doc-content ol {
margin-bottom: 1rem;
padding-left: 1.5rem;
}
.doc-content li {
margin-bottom: 0.5rem;
color: var(--text-secondary);
}
.doc-content strong {
color: var(--text-primary);
font-weight: 600;
}
.doc-content code {
background: var(--bg-tertiary);
padding: 0.125rem 0.375rem;
border-radius: 3px;
font-family: 'SF Mono', Monaco, 'Cascadia Code', monospace;
font-size: 0.875rem;
color: var(--accent-yellow);
}
/* Footer */
footer {
background: var(--bg-secondary);
border-top: 1px solid var(--border-color);
padding: 1.5rem 2rem;
text-align: center;
margin-top: 2rem;
}
footer p {
color: var(--text-secondary);
font-size: 0.875rem;
margin-bottom: 0.25rem;
}
footer a {
color: var(--accent-blue);
text-decoration: none;
}
footer a:hover {
text-decoration: underline;
}
/* Responsive Layout - Technique 3: Media queries with grid-template-areas */
@media (max-width: 1200px) {
main {
grid-template-areas:
"stats stats timeline timeline"
"usage usage usage usage"
"activity activity activity activity"
"performance performance performance performance"
"docs docs docs docs";
grid-template-columns: repeat(4, 1fr);
}
}
@media (max-width: 768px) {
main {
grid-template-areas:
"stats"
"timeline"
"usage"
"activity"
"performance"
"docs";
grid-template-columns: 1fr;
padding: 1rem;
gap: 1rem;
}
header {
padding: 1rem;
}
.panel {
padding: 1rem;
}
.stats-grid {
grid-template-columns: repeat(auto-fit, minmax(100px, 1fr));
}
}
/* Animation */
@keyframes fadeIn {
from { opacity: 0; transform: translateY(10px); }
to { opacity: 1; transform: translateY(0); }
}
.panel {
animation: fadeIn 0.5s ease forwards;
}
.stats-panel { animation-delay: 0.1s; }
.timeline-panel { animation-delay: 0.2s; }
.usage-panel { animation-delay: 0.3s; }
.activity-panel { animation-delay: 0.4s; }
.performance-panel { animation-delay: 0.5s; }
</style>
</head>
<body>
<header>
<h1>📊 Dashboard Layout Tool</h1>
<p class="tagline">Responsive developer analytics dashboard powered by CSS Grid</p>
</header>
<main>
<!-- Stats Panel -->
<section class="panel stats-panel">
<h2><span class="panel-icon">📈</span>Session Overview</h2>
<div class="stats-grid">
<div class="stat-card blue">
<span class="stat-value" id="stat-sessions">24</span>
<span class="stat-label">Sessions</span>
</div>
<div class="stat-card green">
<span class="stat-value" id="stat-messages">1,847</span>
<span class="stat-label">Messages</span>
</div>
<div class="stat-card yellow">
<span class="stat-value" id="stat-tools">432</span>
<span class="stat-label">Tool Calls</span>
</div>
<div class="stat-card purple">
<span class="stat-value" id="stat-hours">18.5h</span>
<span class="stat-label">Active Time</span>
</div>
</div>
</section>
<!-- Timeline Panel -->
<section class="panel timeline-panel">
<h2><span class="panel-icon">🕐</span>Recent Activity</h2>
<div class="timeline">
<div class="timeline-item">
<div class="timeline-time">14:32</div>
<div class="timeline-content">
<div class="timeline-title">
Created dashboard component
<span class="timeline-badge edit">Edit</span>
</div>
<div class="timeline-desc">Modified 3 files in /src/components</div>
</div>
</div>
<div class="timeline-item">
<div class="timeline-time">14:28</div>
<div class="timeline-content">
<div class="timeline-title">
Read configuration files
<span class="timeline-badge read">Read</span>
</div>
<div class="timeline-desc">Analyzed package.json and tsconfig.json</div>
</div>
</div>
<div class="timeline-item">
<div class="timeline-time">14:15</div>
<div class="timeline-content">
<div class="timeline-title">
Ran test suite
<span class="timeline-badge bash">Bash</span>
</div>
<div class="timeline-desc">npm test -- 23 tests passed</div>
</div>
</div>
<div class="timeline-item">
<div class="timeline-time">14:02</div>
<div class="timeline-content">
<div class="timeline-title">
Searched codebase
<span class="timeline-badge search">Search</span>
</div>
<div class="timeline-desc">Found 12 matches for "useEffect"</div>
</div>
</div>
</div>
</section>
<!-- Tool Usage Panel -->
<section class="panel usage-panel">
<h2><span class="panel-icon">🔧</span>Tool Usage Distribution</h2>
<div class="usage-bars" id="usage-chart"></div>
</section>
<!-- Activity Feed Panel -->
<section class="panel activity-panel">
<h2><span class="panel-icon">📋</span>Activity Feed</h2>
<div class="activity-feed" id="activity-feed"></div>
</section>
<!-- Performance Metrics Panel -->
<section class="panel performance-panel">
<h2><span class="panel-icon"></span>Performance Metrics</h2>
<div class="performance-grid">
<div class="metric-card">
<div class="metric-title">Avg Response</div>
<div class="metric-value">2.3s</div>
<div class="metric-bar">
<div class="metric-bar-fill" style="width: 77%;"></div>
</div>
</div>
<div class="metric-card">
<div class="metric-title">Success Rate</div>
<div class="metric-value">94.2%</div>
<div class="metric-bar">
<div class="metric-bar-fill" style="width: 94.2%;"></div>
</div>
</div>
<div class="metric-card">
<div class="metric-title">Token Usage</div>
<div class="metric-value">847K</div>
<div class="metric-bar">
<div class="metric-bar-fill" style="width: 65%;"></div>
</div>
</div>
<div class="metric-card">
<div class="metric-title">Files Modified</div>
<div class="metric-value">142</div>
<div class="metric-bar">
<div class="metric-bar-fill" style="width: 82%;"></div>
</div>
</div>
</div>
</section>
<!-- Documentation -->
<section class="docs">
<h2>About This Tool</h2>
<div class="doc-content">
<h3>Purpose</h3>
<p>A demonstration of CSS Grid Layout techniques applied to create a flexible, responsive developer dashboard for Claude Code analytics. This tool showcases how to build modular dashboard layouts that adapt seamlessly to different screen sizes while maintaining visual hierarchy and usability.</p>
<h3>Features</h3>
<ul>
<li><strong>Named Grid Areas</strong> - Semantic layout regions using <code>grid-template-areas</code></li>
<li><strong>Responsive Auto-Fit</strong> - Stats cards that automatically adjust columns with <code>auto-fit</code> and <code>minmax()</code></li>
<li><strong>Consistent Spacing</strong> - Clean gaps between panels using CSS Grid <code>gap</code> property</li>
<li><strong>Multi-Panel Layout</strong> - 6 distinct dashboard sections arranged in an intelligent grid</li>
<li><strong>Adaptive Breakpoints</strong> - Layout reconfigures at 1200px and 768px for optimal viewing</li>
<li><strong>Dark Developer Theme</strong> - Eye-friendly color scheme for extended coding sessions</li>
<li><strong>Interactive Metrics</strong> - Live data visualization with tool usage, timeline, and performance stats</li>
</ul>
<h3>Web Research Integration</h3>
<p><strong>Source:</strong> <a href="https://developer.mozilla.org/en-US/docs/Web/CSS/CSS_Grid_Layout" target="_blank">MDN - CSS Grid Layout</a></p>
<p><strong>Techniques Applied:</strong></p>
<ul>
<li><strong>grid-template-areas</strong> - Created named layout regions ("stats", "timeline", "usage", "activity", "performance", "docs") for semantic, maintainable dashboard structure. This allows easy reconfiguration at different breakpoints by simply redefining the areas.</li>
<li><strong>auto-fit with minmax()</strong> - Implemented responsive card grids (stats-grid, performance-grid) that automatically adjust column count based on available space using <code>repeat(auto-fit, minmax(120px, 1fr))</code>. Cards flow and resize without media queries.</li>
<li><strong>gap property</strong> - Applied consistent spacing between all grid items using the <code>gap: 1.5rem</code> property, eliminating the need for margin calculations and ensuring uniform visual rhythm across the entire dashboard.</li>
</ul>
<h3>Grid Layout Structure</h3>
<p>The main dashboard uses a 4-column grid with named areas:</p>
<ul>
<li><strong>Desktop (>1200px):</strong> 4x4 grid with stats/timeline sharing top row, usage/activity in middle rows</li>
<li><strong>Tablet (768-1200px):</strong> 4-column grid with full-width sections stacked vertically</li>
<li><strong>Mobile (<768px):</strong> Single column stack for optimal mobile viewing</li>
</ul>
<h3>Usage</h3>
<ol>
<li>Open the tool to see a complete analytics dashboard layout</li>
<li>Resize the browser window to observe responsive grid reconfiguration</li>
<li>Notice how named grid areas reorganize at different breakpoints</li>
<li>Observe auto-fit behavior in stats cards and performance metrics</li>
<li>Use this pattern for building your own modular dashboards</li>
<li>Inspect the CSS to understand grid-template-areas syntax</li>
</ol>
<h3>Developer Notes</h3>
<p>This dashboard demonstrates key advantages of CSS Grid for developer tools:</p>
<ul>
<li><strong>Maintainability:</strong> Named grid areas make layout intent clear and changes simple</li>
<li><strong>Flexibility:</strong> Easy to add, remove, or reorder dashboard panels</li>
<li><strong>Responsiveness:</strong> Auto-fit and minmax() eliminate brittle breakpoint logic</li>
<li><strong>Performance:</strong> Pure CSS solution with no JavaScript layout calculations</li>
<li><strong>Accessibility:</strong> Grid maintains semantic HTML structure regardless of visual layout</li>
</ul>
</div>
</section>
</main>
<footer>
<p>Claude Code DevTools | Generated via web-enhanced infinite loop</p>
<p>Web Source: <a href="https://developer.mozilla.org/en-US/docs/Web/CSS/CSS_Grid_Layout" target="_blank">MDN - CSS Grid Layout</a></p>
</footer>
<script>
// Generate tool usage bars
const toolUsageData = [
{ tool: 'Edit', count: 156, max: 200 },
{ tool: 'Read', count: 142, max: 200 },
{ tool: 'Bash', count: 89, max: 200 },
{ tool: 'Grep', count: 67, max: 200 },
{ tool: 'Write', count: 45, max: 200 },
{ tool: 'Glob', count: 33, max: 200 }
];
const usageChart = document.getElementById('usage-chart');
toolUsageData.forEach(item => {
const percentage = (item.count / item.max * 100).toFixed(1);
const bar = document.createElement('div');
bar.className = 'usage-bar';
bar.innerHTML = `
<div class="usage-label">${item.tool}</div>
<div class="usage-bar-bg">
<div class="usage-bar-fill" style="width: ${percentage}%">
${item.count}
</div>
</div>
`;
usageChart.appendChild(bar);
});
// Generate activity feed
const activities = [
{ type: 'success', icon: '✅', title: 'Successfully deployed to production', meta: '2 minutes ago', class: 'success' },
{ type: 'info', icon: '📝', title: 'Updated README documentation', meta: '15 minutes ago', class: '' },
{ type: 'warning', icon: '⚠️', title: 'Deprecated API usage detected', meta: '32 minutes ago', class: 'warning' },
{ type: 'success', icon: '🧪', title: 'All tests passed (23/23)', meta: '1 hour ago', class: 'success' },
{ type: 'info', icon: '🔍', title: 'Code review requested', meta: '2 hours ago', class: '' },
{ type: 'error', icon: '❌', title: 'Build failed on branch feature-123', meta: '3 hours ago', class: 'error' },
{ type: 'success', icon: '🚀', title: 'Feature flag enabled: dark-mode', meta: '4 hours ago', class: 'success' },
{ type: 'info', icon: '💾', title: 'Database backup completed', meta: '5 hours ago', class: '' }
];
const activityFeed = document.getElementById('activity-feed');
activities.forEach(activity => {
const item = document.createElement('div');
item.className = `activity-item ${activity.class}`;
item.innerHTML = `
<div class="activity-icon">${activity.icon}</div>
<div class="activity-content">
<div class="activity-title">${activity.title}</div>
<div class="activity-meta">${activity.meta}</div>
</div>
`;
activityFeed.appendChild(item);
});
// Animate stats on load
function animateValue(id, start, end, duration) {
const element = document.getElementById(id);
const startTime = performance.now();
function update(currentTime) {
const elapsed = currentTime - startTime;
const progress = Math.min(elapsed / duration, 1);
const current = Math.floor(start + (end - start) * progress);
if (id === 'stat-hours') {
element.textContent = (start + (end - start) * progress).toFixed(1) + 'h';
} else if (id === 'stat-messages') {
element.textContent = current.toLocaleString();
} else {
element.textContent = current;
}
if (progress < 1) {
requestAnimationFrame(update);
}
}
requestAnimationFrame(update);
}
// Trigger animations after page load
window.addEventListener('load', () => {
animateValue('stat-sessions', 0, 24, 1000);
animateValue('stat-messages', 0, 1847, 1200);
animateValue('stat-tools', 0, 432, 1100);
animateValue('stat-hours', 0, 18.5, 1300);
});
// Add keyboard shortcut hint
document.addEventListener('keydown', (e) => {
if (e.ctrlKey && e.key === 'k') {
e.preventDefault();
alert('Keyboard shortcuts:\n\nCtrl+K: This help menu\nCtrl+R: Refresh dashboard\nCtrl+E: Export data');
}
if (e.ctrlKey && e.key === 'r') {
e.preventDefault();
location.reload();
}
if (e.ctrlKey && e.key === 'e') {
e.preventDefault();
alert('Export functionality would trigger here (not implemented in this demo)');
}
});
</script>
</body>
</html>