forked from JohnEarnest/Octo
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathindex.html
308 lines (288 loc) · 13.2 KB
/
index.html
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
<html>
<head>
<title>Octo</title>
<link rel="stylesheet" href="css/styles.css">
</head>
<body>
<div class="menubar">
<a href="https://github.com/JohnEarnest/Octo"><img src="images/logo.png" style="padding-right: 30px;vertical-align: middle;"/></a>
<button type="button" onClick="run()">Run</button>
<button type="button" onClick="compile()">Compile</button>
<button type="button" onClick="share()">Share</button>
<select id="examples" onchange="loadExample()">
<option value="">Examples...</option>
</select>
<select id="framerate" onchange="framerate()">
<option value="7">7 Cycles/Frame</option>
<option value="15">15 Cycles/Frame</option>
<option value="20" selected="selected">20 Cycles/Frame</option>
<option value="30">30 Cycles/Frame</option>
<option value="100">100 Cycles/Frame</option>
<option value="200">200 Cycles/Frame</option>
<option value="500">500 Cycles/Frame</option>
<option value="1000">1000 Cycles/Frame</option>
</select>
<button type="button" onClick="toggleManual();">Manual</button>
<button type="button" onClick="toggleOptions();">Options</button>
<button type="button" onClick="toggleSpriteEditor();">Sprite Editor</button>
<button type="button" onClick="toggleAudioEditor();" class="xofeature" style="display:none" class="xofeature" style="display:none" >Audio Editor</button>
<button type="button" onClick="toggleBinaryTools();">Binary Tools</button>
</div>
<div style="padding-bottom: 40px; position: relative; height: 100%;">
<center>
<div id="manual" class="leftpanel" style="display:none">
<h3>Manual</h3>
<iframe src="https://johnearnest.github.io/Octo/docs/Manual.html" width="450" height="100%"></iframe>
</div>
<textarea id="input" rows="40" cols="100" spellcheck="false">
# Chip8 is a virtual machine designed in 1977 for programming video games.
# Octo is a high level assembler, disassembler and simulator for Chip8.
# Click 'Run' and then press ASWD to move the sprite around the screen.
# Click the Octo logo for source, documentation and examples.
:alias px v3
:alias py v4
: main
px := random 0b0011111
py := random 0b0001111
i := person
sprite px py 8
loop
# erase the player, update its position and then redraw:
sprite px py 8
v0 := 5 if v0 key then py += -1 # keyboard W
v0 := 8 if v0 key then py += 1 # keyboard S
v0 := 7 if v0 key then px += -1 # keyboard A
v0 := 9 if v0 key then px += 1 # keyboard D
sprite px py 8
# lock the framerate of this program via the delay timer:
loop
vf := delay
if vf != 0 then
again
vf := 3
delay := vf
again
: person
0x70 0x70 0x20 0x70 0xA8 0x20 0x50 0x50
</textarea>
<div id="spriteEditor" class="rightpanel" style="display:none">
<h3>Sprite Editor</h3>
<center>
Click and drag to draw.<br/>
Right-click and drag to erase.<br/><br/>
<input type="checkbox" id="spriteEditorSize" onchange="setSpriteEditorSize();">
<label for="spriteEditorSize">16x16 mode</label>
<br/>
<div class="xofeature" style="display:none">
<input type="checkbox" id="spriteEditorColor" onchange="setSpriteEditorColor();">
<label for="spriteEditorColor">Color mode</label>
</div>
<br/>
<canvas id="spriteEditorPalette" width="200px" height="25px" style="display:none;"></canvas><br/>
<canvas id="draw" width="200" height="375" style="border:1px solid;"></canvas><br/>
<textarea id="spriteData" rows="3" cols="25" onchange="editHex();" onkeyup="editHex();"></textarea>
</center>
</div>
<div id="options" class="rightpanel" style="display:none">
<h3>Colors</h3>
<table border=0>
<tr>
<td>Background</td>
<td><input type="text" size="7" id="backEdit" onchange="editBack();" onkeyup="editBack();"></td>
<td bgcolor="0xFF0000" id="backSample" > </td>
</tr>
<tr>
<td>Foreground 1</td>
<td><input type="text" size="7" id="foreEdit1" onchange="editFore1();" onkeyup="editFore1();"></td>
<td bgcolor="0xFF0000" id="foreSample1" > </td>
</tr>
<tr class="xofeature" style="display:none">
<td>Foreground 2 (XO-Chip)</td>
<td><input type="text" size="7" id="foreEdit2" onchange="editFore2();" onkeyup="editFore2();"></td>
<td bgcolor="0xFF0000" id="foreSample2" > </td>
</tr>
<tr class="xofeature" style="display:none">
<td>Blended (XO-Chip)</td>
<td><input type="text" size="7" id="blendEdit" onchange="editBlend();" onkeyup="editBlend();"></td>
<td bgcolor="0xFF0000" id="blendSample" > </td>
</tr>
<tr>
<td>Buzzer</td>
<td><input type="text" size="7" id="buzzEdit" onchange="editBuzz();" onkeyup="editBuzz();"></td>
<td bgcolor="0xFF0000" id="buzzSample" > </td>
</tr>
<tr>
<td>Silence</td>
<td><input type="text" size="7" id="silentEdit" onchange="editSilent();" onkeyup="editSilent();"></td>
<td bgcolor="0xFF0000" id="silentSample" > </td>
</tr>
</table>
<select id="palettePreset" onChange="palettePreset();">
<option value="">Palette Presets...</option>
<option value='classic'>Octo Classic™</option>
<option value='["#FF0000","#FFFF00","#FFFFFF","#000000","#990000","#330000"]'>Hot Dog Stand</option>
<option value='["#306230","#8BAC0F","#9BBC0F","#0F380F","#333333","#000000"]'>Pea Soup LCD</option>
<option value='["#000000","#FFFFFF","#666666","#AAAAAA","#666666","#000000"]'>Grayscale</option>
<option value='["#00FF00","#FF0000","#FFFF00","#000000","#999900","#333300"]'>CGA 0</option>
<option value='["#FF00FF","#00FFFF","#FFFFFF","#000000","#990099","#330033"]'>CGA 1</option>
</select>
<h3>Compatibility</h3>
<table>
<tr>
<td><input type="checkbox" id="shiftQuirks" onchange="setShiftQuirks();"></td>
<td><tt><<=</tt> and <tt>>>=</tt> modify <tt>vx</tt> in place and ignore <tt>vy</tt>.</td>
</tr>
<tr>
<td><input type="checkbox" id="loadStoreQuirks" onchange="setLoadStoreQuirks();"></td>
<td><tt>load</tt> and <tt>store</tt> operations leave <tt>i</tt> unchanged.</td>
</tr>
<tr>
<td><input type="checkbox" id="vfOrderQuirks" onchange="setVfOrderQuirks();"></td>
<td>arithmetic results write to <tt>vf</tt> after status flag.</td>
</tr>
<tr>
<td><input type="checkbox" id="enableXO" onchange="setEnableXO();"></td>
<td>enable XO-Chip extended instruction set.</td>
</tr>
</table>
</div>
<div id="bintools" class="rightpanel" style="display:none">
<h3>Binary Tools</h3>
Note that decompilation can be slow.<br/>
Enter a byte array:<br/>
<textarea id="decompileInput" rows="6" cols="40">[0xD0, 0x15, 0x70, 0x04, 0x40, 0x40, 0x71, 0x05, 0x40, 0x40, 0x60, 0x00, 0x12, 0x00]</textarea><br/>
<button type="button" onclick="decompileStart()">Decompile</button>
<button type="button" onclick="decompileRun()">Run</button>
<button type="button" onclick="decompileFile()">Open File...</button>
<input type="file" id="fileinput" onchange="decompileRequestLoad()" style="display:none">
<h3>Decompiler Options</h3>
<select id="numericFormat" onchange="setNumericFormat();">
<option value='default'>Numeric Format</option>
<option value='hex'>Hexadecimal</option>
<option value='dec'>Decimal</option>
<option value='bin'>Binary</option>
</select>
<table>
<tr>
<td><input type="checkbox" id="maskOverride" onchange="setMaskFormatOverride();"></td>
<td>Format the numeric operand of <tt>random n</tt> as binary</td>
</tr>
</table>
</div>
<div id="audiotools" class="rightpanel" style="display:none">
<h3>Audio Editor</h3>
Enter a pattern of 16 bytes:<br>
<canvas id="drawAudio" width="256" height="32"></canvas></br>
<textarea id="audioPattern" rows="4" cols="40" spellcheck="false" onkeyup="drawAudio();"></textarea><br>
<select id="audioPreset" onchange="presetAudio();">
<option value="">Choose a preset...</option>
<option value="0xFF 0xFF 0xFF 0xFF 0xFF 0xFF 0xFF 0xFF 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0x00">1/2 Duty Square Wave</option>
<option value="0xFF 0xFF 0xFF 0xFF 0x00 0x00 0x00 0x00 0xFF 0xFF 0xFF 0xFF 0x00 0x00 0x00 0x00">1/4 Duty Square Wave</option>
<option value="0xFF 0xFF 0x00 0x00 0xFF 0xFF 0x00 0x00 0xFF 0xFF 0x00 0x00 0xFF 0xFF 0x00 0x00">1/8 Duty Square Wave</option>
<option value="0xFF 0x00 0xFF 0x00 0xFF 0x00 0xFF 0x00 0xFF 0x00 0xFF 0x00 0xFF 0x00 0xFF 0x00">1/16 Duty Square Wave</option>
<option value="0xF0 0xF0 0xF0 0xF0 0xF0 0xF0 0xF0 0xF0 0xF0 0xF0 0xF0 0xF0 0xF0 0xF0 0xF0 0xF0">1/32 Duty Square Wave</option>
<option value="0xCC 0xCC 0xCC 0xCC 0xCC 0xCC 0xCC 0xCC 0xCC 0xCC 0xCC 0xCC 0xCC 0xCC 0xCC 0xCC">1/64 Duty Square Wave</option>
<option value="0xAA 0xAA 0xAA 0xAA 0xAA 0xAA 0xAA 0xAA 0xAA 0xAA 0xAA 0xAA 0xAA 0xAA 0xAA 0xAA">1/128 Duty Square Wave</option>
<option value="0x10 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0x10 0x00 0x00 0x00 0x00 0x00 0x00 0x00">High Grind</option>
<option value="0xAA 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0xAA 0x00 0x00 0x00 0x00 0x00 0x00 0x00">Medium Grind</option>
<option value="0xFF 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0xFF 0x00 0x00 0x00 0x00 0x00 0x00 0x00">Low Grind</option>
<option value="0xF0 0xF0 0xF0 0xF0 0xcc 0xcc 0xcc 0xcc 0xF0 0xF0 0xF0 0xF0 0xcc 0xcc 0xcc 0xcc">Doorbell</option>
<option value="0x55 0xAA 0x55 0xAA 0x55 0xAA 0x55 0xAA 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0x00">Gurgle</option>
<option value="0x02 0xCD 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0x00">Click</option>
<option value="0xFF 0x80 0x3F 0xE0 0x0F 0xF8 0x03 0xFF 0x00 0x7F 0xC0 0x8E 0x38 0xE3 0x8E 0x38">A5</option>
</select>
<button onclick="randomAudio();">Random</button>
<button onclick="shiftAudio(1);"><</button>
<button onclick="shiftAudio(-1);">></button>
<br>
Duration (1/60ths of a second): <input id="time" type="text" size="4" value="30">
<button onclick="playAudio();">Play</button>
<div id="audioerror" style="color: red;"></div>
<h3>Waveform Blending</h3>
Combine this waveform with the one above.<br>
<textarea id="blendPattern" rows="4" cols="40" spellcheck="false"></textarea><br>
<button type="button" onclick="blendWaveform('xor');">XOR</button>
<button type="button" onclick="blendWaveform('and');">AND</button>
<button type="button" onclick="blendWaveform('or');">OR</button>
<button type="button" onclick="blendWaveform('not');">NOT (this pattern)</button>
<button type="button" onclick="swapWaveforms('blendPattern', 'audioPattern');">Swap</button>
<h3>Tone Generator</h3>
<canvas id="waveform" width="256" height="64"></canvas><br>
Freq. (Hz): <input id="frequency" type="text" size="4" value="440" onchange="generateWaveform();" onkeyup="generateWaveform();">
Cutoff: <input id="cutoff" type="text" size="4" value="128" onchange="generateWaveform();" onkeyup="generateWaveform();">
<button type="button" onclick="swapWaveforms('generatedPattern', 'audioPattern');">Swap</button>
<br><textarea id="generatedPattern" rows="4" cols="40" spellcheck="false"></textarea>
</div>
</center>
<center>
<textarea id="output" style="display:none;" rows="6" cols="80"></textarea>
</center>
</div>
<div id="status" class="statusbar"></div>
<div class="lightbox" id="emulator" style="display:none">
<div class="canv">
<canvas id="target" width="640" height="320"></canvas>
<center>
<table border="0" id="keypad" style="display:none">
<tr>
<td class="key" id="0x1">1</td>
<td class="key" id="0x2">2</td>
<td class="key" id="0x3">3</td>
<td class="key" id="0xC">C</td>
</tr>
<tr>
<td class="key" id="0x4">4</td>
<td class="key" id="0x5">5</td>
<td class="key" id="0x6">6</td>
<td class="key" id="0xD">D</td>
</tr>
<tr>
<td class="key" id="0x7">7</td>
<td class="key" id="0x8">8</td>
<td class="key" id="0x9">9</td>
<td class="key" id="0xE">E</td>
</tr>
<tr>
<td class="key" id="0xA">A</td>
<td class="key" id="0x0">0</td>
<td class="key" id="0xB">B</td>
<td class="key" id="0xF">F</td>
</tr>
</table>
</center>
</div>
<div class="buttons">
<img
title="close"
src="images/close.png"
onclick="keyUp({keyCode:27})"
/>
<img
title="toggle keypad"
src="images/keypad.png"
onclick="toggleKeypad()"
style="padding-left: 10px;"
/>
<img
id="continueButton"
title="continue"
src="images/continue.png"
onclick="clearBreakpoint()"
style="padding-left: 10px; display:none;"
/>
</div>
<div class="debugger" id="registerView" style="display:none">
register display.
</div>
</div>
<div class="lightbox" style="display:none" id="decompileWork">
<img src="images/load.gif" class="centericon"/>
</div>
<script src="js/compiler.js"></script>
<script src="js/decompiler.js"></script>
<script src="js/emulator.js"></script>
<script src="js/shared.js"></script>
<script src="js/octo.js"></script>
<script>window.onload = runGist();</script>
</body>
</html>