]> git.cworth.org Git - zombocom-ai/blob - index.html
9989e40608f5946a60353e6f85b6df2bde206410
[zombocom-ai] / index.html
1 <!DOCTYPE html>
2 <html>
3
4 <head>
5   <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
6   <title>ZOMBO</title>
7   <link href="/zombo.css" rel="stylesheet" type="text/css">
8   <meta name="viewport" content="width=device-width,initial-scale=1">
9   <meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
10   <meta name="HandheldFriendly" content="true">
11 </head>
12
13 <body>
14   <div id="content">
15
16     <div id="header" align="center">
17       <p>
18         <br>
19       </p>
20
21       <p>
22         <img src="/zombocom.png" alt="Zombocom" longdesc="http://zombo.com" width="1199" height="217">
23       </p>
24     </div>
25
26     <p>
27       Welcome to Zombocom. You can do anything at Zombocom, anything at
28       all. The only limit is yourself!
29     </p>
30
31     <dialog id="name-dialog">
32       <form method="dialog">
33         <p>
34           <label>Your name:
35             <input id="name" type="text">
36           </label>
37         </p>
38         <div>
39           <button value="cancel">Cancel</button>
40           <button id="confirm" value="default">Confirm</button>
41         </div>
42       </form>
43     </dialog>
44
45     <p>
46       <div id="spinner" align="center">
47         <div class="animate-flicker">
48           <p>
49             <img src="/pngwheel.png" class="rotate thefade">
50           </p>
51         </div>
52       </div>
53
54       <form action="" id="zombo-form">
55         <div class="form-row large">
56           <label for="prompt">
57             What can you imagine?
58           </label>
59           <button id="safety" type="button">Safety prompt</button>
60           <textarea id="prompt" rows="4" width="100%" autocomplete="off" required></textarea>
61         </div>
62
63         <div class="form-row small left">
64           <div class="labeled-row">
65             <label for="code">
66               Numeric code:
67             </label>
68             <input id="code" type="text" autocomplete="off" placeholder="(Leave blank for random)" />
69           </div>
70         </div>
71
72         <div class="form-row large">
73           <button id="generate" type="submit">Make the infinite possible</button>
74         </div>
75       </form>
76     </p>
77
78     <div id="images">
79     </div>
80
81     <ul id="comments">
82     </ul>
83
84     <p>
85       <form action="" id="comment-form">
86         <input id="comment" type="text" style="width:100%" autocomplete="off" placeholder="Add a comment" />
87       </form>
88     </p>
89
90     <audio loop="" src="/zombo_words.mp3" type="audio/mpeg"></audio>
91     <button id="mute" class="menu-button fade volume">
92       <div>🔊</div>
93       <script>
94 const mute = document.querySelector("#mute");
95 const icon = document.querySelector("#mute > div");
96 const audio = document.querySelector("audio");
97
98 mute.addEventListener("click", () => {
99   if (audio.paused) {
100       audio.volume = 0.2;
101       audio.play();
102       icon.innerHTML = "🔈";
103   } else {
104       audio.pause();
105       icon.innerHTML = "🔊";
106   }
107   mute.classList.add("fade");
108 });
109       </script>
110
111     </button>
112
113     <button id="profile" class="menu-button">
114       <div>👤</div>
115     </button>
116
117   </div>
118
119   <script src="/socket.io/socket.io.js"></script>
120   <script>
121     var socket = io();
122
123     const name = document.querySelector("#name");
124     const name_dialog = document.querySelector("#name-dialog");
125     const images = document.querySelector("#images");
126     const comments = document.querySelector("#comments");
127     const comment_form = document.querySelector("#comment-form");
128     const comment = document.querySelector("#comment");
129     const zombo_form = document.querySelector("#zombo-form");
130     const prompt = document.querySelector("#prompt");
131     const code = document.querySelector("#code");
132     const safety= document.querySelector("#safety");
133     const spinner = document.querySelector("#spinner");
134     const profile = document.querySelector("#profile");
135     var spinner_timeout;
136
137     comment.addEventListener('focus', () => {
138         /* Do nothing if name is already set. */
139         if (name.value)
140             return;
141
142         /* Otherwise, bring up the modal dialog to set the name. */
143         name_dialog.showModal();
144     });
145
146     profile.addEventListener('click', () => {
147         name_dialog.showModal();
148     });
149
150     name_dialog.addEventListener('close', () => {
151         socket.emit('set-name', name.value);
152     });
153
154     comment_form.addEventListener('submit', function(e) {
155         e.preventDefault();
156         if (comment.value) {
157             socket.emit('comment', comment.value);
158             comment.value = '';
159         }
160     });
161
162     socket.on('comment', function(msg) {
163         var item = document.createElement('li');
164         item.textContent = msg;
165         comments.appendChild(item);
166     });
167
168     socket.on('inform-name', (name) => {
169         console.log("Received inform-name event: " + name);
170         name.value = name;
171     });
172
173     socket.on('reset', () => {
174         images.replaceChildren();
175     });
176
177     socket.on('image', (image) => {
178         const figure = document.createElement('figure');
179         const img = document.createElement('img');
180         img.src = image.filename;
181         const figcaption = document.createElement('figcaption');
182         const caption_text = document.createTextNode(`${image.prompt} (${image.code})`);
183         figcaption.appendChild(caption_text);
184         figure.appendChild(img);
185         figure.appendChild(figcaption);
186         images.prepend(figure);
187     });
188
189     function hide_spinner() {
190         zombo_form.style.display = "grid";
191         spinner.style.display = "none";
192     }
193
194     zombo_form.addEventListener('submit', function(e) {
195         e.preventDefault();
196         /* Hide the form and show spinner while generation is happening. */
197         zombo_form.style.display = "none";
198         spinner.style.display = "block";
199         spinner_timeout = setTimeout(hide_spinner, 60000);
200         socket.emit('generate', {"prompt": prompt.value, "code": code.value});
201         prompt.value = '';
202     });
203
204     socket.on('generation-done', () => {
205         /* Re-display the form and hide spinner now that generation is over. */
206         clearTimeout(spinner_timeout);
207         hide_spinner();
208     });
209
210     function random_from(items) {
211         return items[Math.floor(Math.random()*items.length)];
212     }
213
214     safety.addEventListener("click", () => {
215         const art_type = [
216             "A portrait of",
217             "A hyperrealistic photograph of",
218             "A matte painting of",
219             "Epic fantasy card art of",
220             "Professional oil painting of",
221             "An image of",
222             "A pencil sketch of",
223             "A watercolor of",
224         ];
225         const subject = [
226             " a modern home",
227             " crashing waves",
228             " a Porsche 911 Carrera",
229             " a Halo spartan",
230             " a cute cat",
231             " a mad scientist",
232             " an elfin princess",
233             " sci-fi buildings",
234             " pastel purple clouds",
235             " a Teenage Mutant Ninja Turtle",
236         ];
237         const scenery = [
238             " in tropical surroundings",
239             " in space",
240             " in an ocean storm",
241             " in a snowy forest",
242             " in a cardboard box",
243             " holding an axe",
244             " in an epic landscape",
245             " in a haunted forest",
246             " riding a motorbike",
247             " in a futuristic city at night",
248             " in a dystopian landscape, foggy",
249             " in the land of snow",
250             " that looks like a watermelon",
251             " on the streets of London at night with neon lights flashing",
252             " that is part octopus",
253             " melting into a puddle",
254         ];
255         const artist = [
256             ", unreal engine 5",
257             ", concept art",
258             ", graphic novel",
259             " by Vincent Van Gogh",
260             " by Claude Monet",
261             " by Johannes Vermeer",
262             ", fantasy art, neon fog",
263             ", epic lighting from above",
264             ", trending on artstation",
265         ];
266
267         prompt.value = random_from(art_type) + random_from(subject) +
268             random_from(scenery) + random_from(artist);
269         return false;
270     });
271
272   </script>
273 </body>
274 </html>