Телеграмма
----------
Сегодня я хочу рассказать, как с помощью самых современных техноголий можно создать маленькую машину времени, которая отправит нас обратно в 80-е.
Ведь именно в 80х, небезызвестной фирмой Sinclair Research (в то время ещё Science of Cambridge Ltd.) был произведён компьютер Sinclair ZX80 (фотография - Daniel Ryde, Skövde 2004-08-31):
По сравнению с ZX81 или ZX-Spectrum, ZX80 не пользовался особой популярностью (что не помешало продать более 50 000 экземпляров). Столь высокие (на то время) продажи, очевидно, обусловлены низкой ценой компьютера (менее $200).
В ZX80 использовалось около 20 микросхем, 4 из корорых - ОЗУ (2 штуки), ПЗУ и процессор. В отличии от следующих моделей (ZX81 и Spectrum), не использовалось никаких ПЛМ (ULA), а только простые, доступные микросхемы.
В компьютере, по сути, не было никакого видеоконтроллера, и изображение формировалось специальной подпрограммой в ПЗУ.
Благодаря этой "особенности", изображение было не всё время, а только когда компьютер ничем не занят. Если же исполнялась программа, то изображение пропадало (да оно пропадало даже при наборе текста! Если бы у меня был реальный ZX80, меня бы это жутко бесило).
JavaScript
Javascript-а на ZX80 не было :)
Вдохновлённый эмулятором NES и ZX-Spectrum 48 на javascript, я решил сделать эмулятор Sinclair ZX80. Так как ZX80 предельно прост, то компонентов всего два - эмулятор Z80 и эмулятор компьютера.
zame-js-z80
У меня уже было ядро Z80, написанное для моего нового эмулятора ZX-Spectrum. Правда, у него был один большой недостаток - оно написано на C :) , но через несколько часов беспрерывной работы, я получил вариант на javascript.
Так как javascript гораздо медленнее, чем компилированный код на C, пришлось узнать много нового о внутреннем представлении чисел в javascript, и освежить в памяти приоритеты операторов.
Я был очень рад тому, что [ -1 & 0xFF = 0xFF ]. Это позволило упростить выражения вида [ (a - b + 0x100) & 0xFF ] до [ (a - b) & 0xFF ]
(эх, а на C всего лишь [ (uint_8)(a - b) ])
Не менее рад я был тому, что [ a + b & 0xFF = (a + b) & 0xFF ], это позволило убрать много ненужных скобочек (я не уверен, что все JS движки способны убирать лишние скобки на этапе компиляции)
Затем я прогнал код через пост-процессор, который используя всю мощь регэкспов, заменил всё что можно посчитать заранее, на готовые значения (например, 0x80 | 0x01 -> 0x81), ведь я ещё менее уверен, что все JS движки способны производить такие оптимизации.
И наконец, я более чем уверен, что JS движки не будут оптимизировать код вида:
var a = 2;
alert(a + 1);
до
alert(3)
(хотя, кажется, Google closure compiler это умеет), так что в критичных местах все переменные, которые не меняют своего значения, были заменени просто цифрами.
js-zx8x
Эмулятор самого компьютера прост как топор. Единственное, что пришлось сделать, так это чтобы нажатая кнопка оставалась нажатой некоторое время, даже если её отпустили (o_O), так как обычный жалкий кусок мяса успевает отпустить кнопку быстрее, чем код в ПЗУ ZX80 на неё отреагировать.
NoCanvas
И самое главное, как вывести изображение без канваса?
На самом деле очень просто - экран в ZX80 текстовый, так что при большом желании, можно выводить изображение хоть в textarea :) , однако, технология CSS-Sprites позволяет достить гораздо большего реализма.
P.S.
В хроме работает на отличненько, кушает от 30% до 50% процессора.
В опере тоже достаточно хорошо (а говорят, что в новой версии оперы совсем летать всё будет).
В файрфоксе заметно притормаживает.
В IE... работает.
Так как я никогда не видел ZX80 вживую, то не могу сказать насколько скорость эмуляции соответствует реальности. По сравнению с другими эмуляторами (теми что я смог найти под Linux), работает быстрее чем положено.
Manual
На случай если вы никогда не имели дела с ZX80, ZX81 или ZX-Spectrum, даю инструкцию по запуску единственной игры для ZX80, которую мне удалось найти (для ZX81 их гораздо больше, а уж под спектрум так совсем уйма);
1) После загрузки страницы, дождитесь появления буквы K на чёрном фоне у углу эмулятора.
2) Нажмите кнопку "Load game" (справа от эмулятора), появится листинг программы
3) Нажмите на кнопку R - должно напечататься RUN
4) Нажмите на ENTER и ожидайте инициализации игры
В самой игре: 6 - влево, 8 - вправо, 0 - стрелять.
Удачного спасения земли от космических пришельцев :)
Links
Поностальгировать - http://nocanvas.zame-dev.org/0004/
Сорсы - http://nocanvas.zame-dev.org/0004/js-zx8x-src.tar.gz
Manual
На случай если вы никогда не имели дела с ZX80, ZX81 или ZX-Spectrum, даю инструкцию по запуску единственной игры для ZX80, которую мне удалось найти (для ZX81 их гораздо больше, а уж под спектрум так совсем уйма);
1) После загрузки страницы, дождитесь появления буквы K на чёрном фоне у углу эмулятора.
2) Нажмите кнопку "Load game" (справа от эмулятора), появится листинг программы
3) Нажмите на кнопку R - должно напечататься RUN
4) Нажмите на ENTER и ожидайте инициализации игры
В самой игре: 6 - влево, 8 - вправо, 0 - стрелять.
Удачного спасения земли от космических пришельцев :)
Links
Поностальгировать - http://nocanvas.zame-dev.org/0004/
Сорсы - http://nocanvas.zame-dev.org/0004/js-zx8x-src.tar.gz
P.P.S.
Выверять текст и дописывать мелочи буду завтра.
Good work. I tried a ZX81 rom on it. It partially works. Commands are OK but not extended. Example PRINT 10-3 gives 1. Did you tried with a ZX81 rom?
ReplyDeleteYours