Buckets:
| <!-- | |
| THIS IS A TEMPLATE THAT SHOULD BE USED EVERY TIME AND MODIFIED. | |
| WHAT TO KEEP: | |
| ✓ Overall structure (header, sidebar, main content) | |
| ✓ Anthropic branding (colors, fonts, layout) | |
| ✓ Seed navigation section (always include this) | |
| ✓ Self-contained artifact (everything inline) | |
| WHAT TO CREATIVELY EDIT: | |
| ✗ The p5.js algorithm (implement YOUR vision) | |
| ✗ The parameters (define what YOUR art needs) | |
| ✗ The UI controls (match YOUR parameters) | |
| Let your philosophy guide the implementation. | |
| The world is your oyster - be creative! | |
| --> | |
| <html lang="en"> | |
| <head> | |
| <meta charset="UTF-8"> | |
| <meta name="viewport" content="width=device-width, initial-scale=1.0"> | |
| <title>Generative Art Viewer</title> | |
| <script src="https://cdnjs.cloudflare.com/ajax/libs/p5.js/1.7.0/p5.min.js"></script> | |
| <link rel="preconnect" href="https://fonts.googleapis.com"> | |
| <link rel="preconnect" href="https://fonts.gstatic.com" crossorigin> | |
| <link href="https://fonts.googleapis.com/css2?family=Poppins:wght@400;500;600&family=Lora:wght@400;500&display=swap" rel="stylesheet"> | |
| <style> | |
| /* Anthropic Brand Colors */ | |
| :root { | |
| --anthropic-dark: #141413; | |
| --anthropic-light: #faf9f5; | |
| --anthropic-mid-gray: #b0aea5; | |
| --anthropic-light-gray: #e8e6dc; | |
| --anthropic-orange: #d97757; | |
| --anthropic-blue: #6a9bcc; | |
| --anthropic-green: #788c5d; | |
| } | |
| * { | |
| margin: 0; | |
| padding: 0; | |
| box-sizing: border-box; | |
| } | |
| body { | |
| font-family: 'Poppins', sans-serif; | |
| background: linear-gradient(135deg, var(--anthropic-light) 0%, #f5f3ee 100%); | |
| min-height: 100vh; | |
| color: var(--anthropic-dark); | |
| } | |
| .container { | |
| display: flex; | |
| min-height: 100vh; | |
| padding: 20px; | |
| gap: 20px; | |
| } | |
| /* Sidebar */ | |
| .sidebar { | |
| width: 320px; | |
| flex-shrink: 0; | |
| background: rgba(255, 255, 255, 0.95); | |
| backdrop-filter: blur(10px); | |
| padding: 24px; | |
| border-radius: 12px; | |
| box-shadow: 0 10px 30px rgba(20, 20, 19, 0.1); | |
| overflow-y: auto; | |
| overflow-x: hidden; | |
| } | |
| .sidebar h1 { | |
| font-family: 'Lora', serif; | |
| font-size: 24px; | |
| font-weight: 500; | |
| color: var(--anthropic-dark); | |
| margin-bottom: 8px; | |
| } | |
| .sidebar .subtitle { | |
| color: var(--anthropic-mid-gray); | |
| font-size: 14px; | |
| margin-bottom: 32px; | |
| line-height: 1.4; | |
| } | |
| /* Control Sections */ | |
| .control-section { | |
| margin-bottom: 32px; | |
| } | |
| .control-section h3 { | |
| font-size: 16px; | |
| font-weight: 600; | |
| color: var(--anthropic-dark); | |
| margin-bottom: 16px; | |
| display: flex; | |
| align-items: center; | |
| gap: 8px; | |
| } | |
| .control-section h3::before { | |
| content: '•'; | |
| color: var(--anthropic-orange); | |
| font-weight: bold; | |
| } | |
| /* Seed Controls */ | |
| .seed-input { | |
| width: 100%; | |
| background: var(--anthropic-light); | |
| padding: 12px; | |
| border-radius: 8px; | |
| font-family: 'Courier New', monospace; | |
| font-size: 14px; | |
| margin-bottom: 12px; | |
| border: 1px solid var(--anthropic-light-gray); | |
| text-align: center; | |
| } | |
| .seed-input:focus { | |
| outline: none; | |
| border-color: var(--anthropic-orange); | |
| box-shadow: 0 0 0 2px rgba(217, 119, 87, 0.1); | |
| background: white; | |
| } | |
| .seed-controls { | |
| display: grid; | |
| grid-template-columns: 1fr 1fr; | |
| gap: 8px; | |
| margin-bottom: 8px; | |
| } | |
| .regen-button { | |
| margin-bottom: 0; | |
| } | |
| /* Parameter Controls */ | |
| .control-group { | |
| margin-bottom: 20px; | |
| } | |
| .control-group label { | |
| display: block; | |
| font-size: 14px; | |
| font-weight: 500; | |
| color: var(--anthropic-dark); | |
| margin-bottom: 8px; | |
| } | |
| .slider-container { | |
| display: flex; | |
| align-items: center; | |
| gap: 12px; | |
| } | |
| .slider-container input[type="range"] { | |
| flex: 1; | |
| height: 4px; | |
| background: var(--anthropic-light-gray); | |
| border-radius: 2px; | |
| outline: none; | |
| -webkit-appearance: none; | |
| } | |
| .slider-container input[type="range"]::-webkit-slider-thumb { | |
| -webkit-appearance: none; | |
| width: 16px; | |
| height: 16px; | |
| background: var(--anthropic-orange); | |
| border-radius: 50%; | |
| cursor: pointer; | |
| transition: all 0.2s ease; | |
| } | |
| .slider-container input[type="range"]::-webkit-slider-thumb:hover { | |
| transform: scale(1.1); | |
| background: #c86641; | |
| } | |
| .slider-container input[type="range"]::-moz-range-thumb { | |
| width: 16px; | |
| height: 16px; | |
| background: var(--anthropic-orange); | |
| border-radius: 50%; | |
| border: none; | |
| cursor: pointer; | |
| transition: all 0.2s ease; | |
| } | |
| .value-display { | |
| font-family: 'Courier New', monospace; | |
| font-size: 12px; | |
| color: var(--anthropic-mid-gray); | |
| min-width: 60px; | |
| text-align: right; | |
| } | |
| /* Color Pickers */ | |
| .color-group { | |
| margin-bottom: 16px; | |
| } | |
| .color-group label { | |
| display: block; | |
| font-size: 12px; | |
| color: var(--anthropic-mid-gray); | |
| margin-bottom: 4px; | |
| } | |
| .color-picker-container { | |
| display: flex; | |
| align-items: center; | |
| gap: 8px; | |
| } | |
| .color-picker-container input[type="color"] { | |
| width: 32px; | |
| height: 32px; | |
| border: none; | |
| border-radius: 6px; | |
| cursor: pointer; | |
| background: none; | |
| padding: 0; | |
| } | |
| .color-value { | |
| font-family: 'Courier New', monospace; | |
| font-size: 12px; | |
| color: var(--anthropic-mid-gray); | |
| } | |
| /* Buttons */ | |
| .button { | |
| background: var(--anthropic-orange); | |
| color: white; | |
| border: none; | |
| padding: 10px 16px; | |
| border-radius: 6px; | |
| font-size: 14px; | |
| font-weight: 500; | |
| cursor: pointer; | |
| transition: all 0.2s ease; | |
| width: 100%; | |
| } | |
| .button:hover { | |
| background: #c86641; | |
| transform: translateY(-1px); | |
| } | |
| .button:active { | |
| transform: translateY(0); | |
| } | |
| .button.secondary { | |
| background: var(--anthropic-blue); | |
| } | |
| .button.secondary:hover { | |
| background: #5a8bb8; | |
| } | |
| .button.tertiary { | |
| background: var(--anthropic-green); | |
| } | |
| .button.tertiary:hover { | |
| background: #6b7b52; | |
| } | |
| .button-row { | |
| display: flex; | |
| gap: 8px; | |
| } | |
| .button-row .button { | |
| flex: 1; | |
| } | |
| /* Canvas Area */ | |
| .canvas-area { | |
| flex: 1; | |
| display: flex; | |
| align-items: center; | |
| justify-content: center; | |
| min-width: 0; | |
| } | |
| #canvas-container { | |
| width: 100%; | |
| max-width: 1000px; | |
| border-radius: 12px; | |
| overflow: hidden; | |
| box-shadow: 0 20px 40px rgba(20, 20, 19, 0.1); | |
| background: white; | |
| } | |
| #canvas-container canvas { | |
| display: block; | |
| width: 100% ; | |
| height: auto ; | |
| } | |
| /* Loading State */ | |
| .loading { | |
| display: flex; | |
| align-items: center; | |
| justify-content: center; | |
| font-size: 18px; | |
| color: var(--anthropic-mid-gray); | |
| } | |
| /* Responsive - Stack on mobile */ | |
| @media (max-width: 600px) { | |
| .container { | |
| flex-direction: column; | |
| } | |
| .sidebar { | |
| width: 100%; | |
| } | |
| .canvas-area { | |
| padding: 20px; | |
| } | |
| } | |
| </style> | |
| </head> | |
| <body> | |
| <div class="container"> | |
| <!-- Control Sidebar --> | |
| <div class="sidebar"> | |
| <!-- Headers (CUSTOMIZE THIS FOR YOUR ART) --> | |
| <h1>TITLE - EDIT</h1> | |
| <div class="subtitle">SUBHEADER - EDIT</div> | |
| <!-- Seed Section (ALWAYS KEEP THIS) --> | |
| <div class="control-section"> | |
| <h3>Seed</h3> | |
| <input type="number" id="seed-input" class="seed-input" value="12345" onchange="updateSeed()"> | |
| <div class="seed-controls"> | |
| <button class="button secondary" onclick="previousSeed()">← Prev</button> | |
| <button class="button secondary" onclick="nextSeed()">Next →</button> | |
| </div> | |
| <button class="button tertiary regen-button" onclick="randomSeedAndUpdate()">↻ Random</button> | |
| </div> | |
| <!-- Parameters Section (CUSTOMIZE THIS FOR YOUR ART) --> | |
| <div class="control-section"> | |
| <h3>Parameters</h3> | |
| <!-- Particle Count --> | |
| <div class="control-group"> | |
| <label>Particle Count</label> | |
| <div class="slider-container"> | |
| <input type="range" id="particleCount" min="1000" max="10000" step="500" value="5000" oninput="updateParam('particleCount', this.value)"> | |
| <span class="value-display" id="particleCount-value">5000</span> | |
| </div> | |
| </div> | |
| <!-- Flow Speed --> | |
| <div class="control-group"> | |
| <label>Flow Speed</label> | |
| <div class="slider-container"> | |
| <input type="range" id="flowSpeed" min="0.1" max="2.0" step="0.1" value="0.5" oninput="updateParam('flowSpeed', this.value)"> | |
| <span class="value-display" id="flowSpeed-value">0.5</span> | |
| </div> | |
| </div> | |
| <!-- Noise Scale --> | |
| <div class="control-group"> | |
| <label>Noise Scale</label> | |
| <div class="slider-container"> | |
| <input type="range" id="noiseScale" min="0.001" max="0.02" step="0.001" value="0.005" oninput="updateParam('noiseScale', this.value)"> | |
| <span class="value-display" id="noiseScale-value">0.005</span> | |
| </div> | |
| </div> | |
| <!-- Trail Length --> | |
| <div class="control-group"> | |
| <label>Trail Length</label> | |
| <div class="slider-container"> | |
| <input type="range" id="trailLength" min="2" max="20" step="1" value="8" oninput="updateParam('trailLength', this.value)"> | |
| <span class="value-display" id="trailLength-value">8</span> | |
| </div> | |
| </div> | |
| </div> | |
| <!-- Colors Section (OPTIONAL - CUSTOMIZE OR REMOVE) --> | |
| <div class="control-section"> | |
| <h3>Colors</h3> | |
| <!-- Color 1 --> | |
| <div class="color-group"> | |
| <label>Primary Color</label> | |
| <div class="color-picker-container"> | |
| <input type="color" id="color1" value="#d97757" onchange="updateColor('color1', this.value)"> | |
| <span class="color-value" id="color1-value">#d97757</span> | |
| </div> | |
| </div> | |
| <!-- Color 2 --> | |
| <div class="color-group"> | |
| <label>Secondary Color</label> | |
| <div class="color-picker-container"> | |
| <input type="color" id="color2" value="#6a9bcc" onchange="updateColor('color2', this.value)"> | |
| <span class="color-value" id="color2-value">#6a9bcc</span> | |
| </div> | |
| </div> | |
| <!-- Color 3 --> | |
| <div class="color-group"> | |
| <label>Accent Color</label> | |
| <div class="color-picker-container"> | |
| <input type="color" id="color3" value="#788c5d" onchange="updateColor('color3', this.value)"> | |
| <span class="color-value" id="color3-value">#788c5d</span> | |
| </div> | |
| </div> | |
| </div> | |
| <!-- Actions Section (ALWAYS KEEP THIS) --> | |
| <div class="control-section"> | |
| <h3>Actions</h3> | |
| <div class="button-row"> | |
| <button class="button" onclick="resetParameters()">Reset</button> | |
| </div> | |
| </div> | |
| </div> | |
| <!-- Main Canvas Area --> | |
| <div class="canvas-area"> | |
| <div id="canvas-container"> | |
| <div class="loading">Initializing generative art...</div> | |
| </div> | |
| </div> | |
| </div> | |
| <script> | |
| // ═══════════════════════════════════════════════════════════════════════ | |
| // GENERATIVE ART PARAMETERS - CUSTOMIZE FOR YOUR ALGORITHM | |
| // ═══════════════════════════════════════════════════════════════════════ | |
| let params = { | |
| seed: 12345, | |
| particleCount: 5000, | |
| flowSpeed: 0.5, | |
| noiseScale: 0.005, | |
| trailLength: 8, | |
| colorPalette: ['#d97757', '#6a9bcc', '#788c5d'] | |
| }; | |
| let defaultParams = {...params}; // Store defaults for reset | |
| // ═══════════════════════════════════════════════════════════════════════ | |
| // P5.JS GENERATIVE ART ALGORITHM - REPLACE WITH YOUR VISION | |
| // ═══════════════════════════════════════════════════════════════════════ | |
| let particles = []; | |
| let flowField = []; | |
| let cols, rows; | |
| let scl = 10; // Flow field resolution | |
| function setup() { | |
| let canvas = createCanvas(1200, 1200); | |
| canvas.parent('canvas-container'); | |
| initializeSystem(); | |
| // Remove loading message | |
| document.querySelector('.loading').style.display = 'none'; | |
| } | |
| function initializeSystem() { | |
| // Seed the randomness for reproducibility | |
| randomSeed(params.seed); | |
| noiseSeed(params.seed); | |
| // Clear particles and recreate | |
| particles = []; | |
| // Initialize particles | |
| for (let i = 0; i < params.particleCount; i++) { | |
| particles.push(new Particle()); | |
| } | |
| // Calculate flow field dimensions | |
| cols = floor(width / scl); | |
| rows = floor(height / scl); | |
| // Generate flow field | |
| generateFlowField(); | |
| // Clear background | |
| background(250, 249, 245); // Anthropic light background | |
| } | |
| function generateFlowField() { | |
| // fill this in | |
| } | |
| function draw() { | |
| // fill this in | |
| } | |
| // ═══════════════════════════════════════════════════════════════════════ | |
| // PARTICLE SYSTEM - CUSTOMIZE FOR YOUR ALGORITHM | |
| // ═══════════════════════════════════════════════════════════════════════ | |
| class Particle { | |
| constructor() { | |
| // fill this in | |
| } | |
| // fill this in | |
| } | |
| // ═══════════════════════════════════════════════════════════════════════ | |
| // UI CONTROL HANDLERS - CUSTOMIZE FOR YOUR PARAMETERS | |
| // ═══════════════════════════════════════════════════════════════════════ | |
| function updateParam(paramName, value) { | |
| // fill this in | |
| } | |
| function updateColor(colorId, value) { | |
| // fill this in | |
| } | |
| // ═══════════════════════════════════════════════════════════════════════ | |
| // SEED CONTROL FUNCTIONS - ALWAYS KEEP THESE | |
| // ═══════════════════════════════════════════════════════════════════════ | |
| function updateSeedDisplay() { | |
| document.getElementById('seed-input').value = params.seed; | |
| } | |
| function updateSeed() { | |
| let input = document.getElementById('seed-input'); | |
| let newSeed = parseInt(input.value); | |
| if (newSeed && newSeed > 0) { | |
| params.seed = newSeed; | |
| initializeSystem(); | |
| } else { | |
| // Reset to current seed if invalid | |
| updateSeedDisplay(); | |
| } | |
| } | |
| function previousSeed() { | |
| params.seed = Math.max(1, params.seed - 1); | |
| updateSeedDisplay(); | |
| initializeSystem(); | |
| } | |
| function nextSeed() { | |
| params.seed = params.seed + 1; | |
| updateSeedDisplay(); | |
| initializeSystem(); | |
| } | |
| function randomSeedAndUpdate() { | |
| params.seed = Math.floor(Math.random() * 999999) + 1; | |
| updateSeedDisplay(); | |
| initializeSystem(); | |
| } | |
| function resetParameters() { | |
| params = {...defaultParams}; | |
| // Update UI elements | |
| document.getElementById('particleCount').value = params.particleCount; | |
| document.getElementById('particleCount-value').textContent = params.particleCount; | |
| document.getElementById('flowSpeed').value = params.flowSpeed; | |
| document.getElementById('flowSpeed-value').textContent = params.flowSpeed; | |
| document.getElementById('noiseScale').value = params.noiseScale; | |
| document.getElementById('noiseScale-value').textContent = params.noiseScale; | |
| document.getElementById('trailLength').value = params.trailLength; | |
| document.getElementById('trailLength-value').textContent = params.trailLength; | |
| // Reset colors | |
| document.getElementById('color1').value = params.colorPalette[0]; | |
| document.getElementById('color1-value').textContent = params.colorPalette[0]; | |
| document.getElementById('color2').value = params.colorPalette[1]; | |
| document.getElementById('color2-value').textContent = params.colorPalette[1]; | |
| document.getElementById('color3').value = params.colorPalette[2]; | |
| document.getElementById('color3-value').textContent = params.colorPalette[2]; | |
| updateSeedDisplay(); | |
| initializeSystem(); | |
| } | |
| // Initialize UI on load | |
| window.addEventListener('load', function() { | |
| updateSeedDisplay(); | |
| }); | |
| </script> | |
| </body> | |
| </html> |
Xet Storage Details
- Size:
- 20.8 kB
- Xet hash:
- 5b2464b69b5fc3b695737b2374b181425a39a33c600e541fd9985d44663511ec
·
Xet efficiently stores files, intelligently splitting them into unique chunks and accelerating uploads and downloads. More info.