Как продолжать жить, не переставая програмить; или - живём в плагине WC

Жизнь в среде накладывает свои ограничения на любое творчество.
Ибо — ты в песочнице, созданной её творцом.

Но, не будем о риллайф, всё это и так всем знакомо. Поговорим о среде, в которой работают плагины для WildCommander, и о том — что и как там можно использовать настолько резвым и эгоистичным кодерам как мы с вами.

Речь будет о только что законченом мною плаге, под названием MaxiClock.
По сути, плаг представляет собою флип-часы.


Итак, идея появилась после упоминания @kowalski о том, что он что-то подобное сделал на Ruby в виде развлечения. Небольшой проброс по гуглу привёл к находке симпатичного набора спрайтов переворота цифр. идея понравилась, файл отложен на будущее.



Проходит несколько месяцев.
У меня ожидаемый, построенный мною роман. это захватывающе, это бесподобно, я рад что всё получилось.
Но эти затянувшиеся, изматывающие и утомляющие игры через месяц надоедают. И я пытаюсь найти время для себя и для увлечений.
Кодить — охота. И пусть идея плага уже не настолько молода, но сексуальна и всё так-же желанна ;)

Первоначальный png файл имел размеры 72х4952 точки. разложив его на листе 512х512, я увидел небольшой перебор — в стандартный слой для тайловой графики весь набор не умещался. Ок, пересчитываем, жмём редактором, получаем заветные 128кб графы, можно вонзить свой ум в код.

первая раскладка графики была удачной — все цифры в блоке есть, всё сконверчено под размер слоя тайлов, пора строить таблицы и кодить вывод.

Я работаю над подобными вещами циклически ( привет @Flexx! ), прорабатывая идею от первоначальной до того варианта, когда уже — хорошо, получилось задуманное. И вот тогда — начинается самая славная игра :)

Итак, построив расположение каждой цифры, добавив вывод её в тайловый слой, я понял что нужно отработать главный эффект — переворот.
часы показывают заданные числа, но увы — нет главного эффекта — флипа! :)
Чтение часов достаю из старых проектов — читаем глюк-часы, отпирая 7й бит rtc:
ld bc,#eff7 : out (c),a
— здесь всё находится в bcd, это довольно прикольно и не привычно.
разложив на тетрады, получаем старшее и младшее значение для каждой позиции часов.
далее я начал писать обработчик этих позиций.
читаем содержимое часов, складываем в память.
разделяя тетрады — обрабатываем каждую часть подпрограммой, в которой — сравниваем изменения относительно предыдущего фрейма.
есть изменения? выбираем адрес нового тайла для отображения, выводим.

вродь просто.

но! нужны флипы, в которых и есть суть часов — выводы промежуточных кадров переворота цифр позиции.
их стоит обрабатывать в момент, когда появилось новое значение для часов / минут / секунд.
юзаем флаг, устанавливающийся в момент изменения времени для данной позиции (секунды и т.д.), который запускает отдельную ветку — проматывающую кадры каждые 25 фреймов до наступления необходимого следующего кадра — новой цифры позиции.

Эффект работает. Уже ништяк. Но код — говно совсем, 6 практически одинаковых процедур для каждой позиции.
ацтой вообще, и дико редкий — но идея уже воплощена.

Стоит всё это сделать в виде скринсейвера для коммандера.

проходят дни, недели, слишком много тяжёлого в отношениях, и хрен ты чем либо другим займёшься.

Сваливаю к чертям. не спеша ухожу.

Вечер. Спокойно. Тихо. Сам. Да, лучше самому.
наконец-то.

Для начала — оптимизация. все данные часов складываем в таблицу. для таблицы оформляем структуру.
структуру использует одна для всех подпрограмма, использующая индексный регистр и данные таблицы с форматом структуры. выглядит — отлично, оптимально, красиво, удобно.
и работает.

итак, что у нас в песочнице WC? начинаем исследования.
так, каков формат плага? куда плагин загружен? какую память можно использовать? какие вообще ограничения блин?
копаю доку, потихоньку проясняется — для плагов есть свой формат с указанием количества выделенных для него паг, кол-во данных при подгрузке плага, способ запуска, название и т.д.

оформляю более-менее под требования. заинтересованным — стоит пройти по этой ссылке.

самому как-то странно и пусто. охота чем-то заняться, и есть старый проект.
плаг, ты симпатичный, я тебя доделаю :)

и вот я внутри.
в песочнице.
песочница — без бордюров, без ограничений. можно копать лопаткой и разбрасывать песочек куда угодно. но увы, выйти из неё в таком случае — не получится.
в коммандер ты не вернёшься, если захочешь писать как привык — управляя ресурсами и памятью по своему усмотрению.

внезапно знакомлюсь

— система выделяет для плагов свою свободную память. часто — это страницы от #20-й, размером с 1 метр.
в этой же странице, по моим наблюдениям, расположен графический (текстовый) экран коммандера.
есть отдельные системные адреса, указывающие на номера включенных паг для каждого окна: #6000 — #6003, которые прямо указывают на номера паг page0 — page3. Сама система не особо манипулирует памятью, но стоит отметить, что банки от #F0 точно не стоит использовать. Кроме того, с 0 по #4000 по умолчанию при запуске находится пага с данными каталогов FAT SD карты, к которым обращается драйвер.
и портить их совершенно не стоит ;) а то придётся слушать мерлина менсона и приходить в себя.

оу, мы действительно встречаемся

ок, память такая память, но уже есть зацепка — свою пагу мы можем получить.
как получить паги для данных, которые идут за кодовым блоком? поможет релятивный адрес для dma.

но тут блин оказывается, что для плага выделено максимум 96 кб. а у меня — только графики на 128кб. отлично.
ЖАТЬ ВСЕ ДАННЫЕ? да блин! не нравится! — скорость старта, в первую очередь.
@TSL подсказывает, что рамка в 8 пикселов по контуру у всех чисел практически идентична — и это уже поле для оптимизации.
снова режу, снова раскладываю, провожу тесты.

подходит.
эта оптимизация сводит размер к 76кб, что уже огромный прирост. да, за счёт усложнения кода. но — так умнее.
очередная промежуточная версия снова отлажена.
идём в организацию плага с готовым кодом.

она — супер! она — супер! она — супер супер супер!

WC
находясь в системе — ты не особо знаешь где ты. возьми номер своей паги из четырёх адресов от #6000, и используй внутреннее апи дма для передачи данных — оно использует внутренний пересчёт паг. нужно использовать релятивные адреса паг. это немного усложняет код, но положительно сказывается на стабильности :)
то-же касается и, возможно, свободных для использования страниц — обычно, повторюсь, это страницы с 32, размером в 1 мб.
В коммандере есть довольно большой набор функций, которые делают всевозможные вещи — работа с картой, выводы окна в текстовом режиме, переключение графических режимов и тому подобное. большая библиотека функций со своими параметрами.
Обнаружено, что работы с тайлами и спрайтами в коммандере — нет. сам включил, сам — выключил.

зачем это нужно?
во первых, плаг работает в системе, в которой есть своё распределение памяти, есть включенные в данный момент окна памяти, и в которой есть свой обработчик прерываний.
тебе охота норм вернуться в коммандер?
так будь аккуратен.

При разработке плага выяснилась недокументировнные особенности — коммандер стабильно держит открытым бит порта #eff7 для чтения клавиатуры/rtc, что доставило — мне тоже нужны были данные оттуда. закрывая порт — я получал неработоспособный UI системы — всё работает, но клавиатура не опрашивается, и часы показывают FF:FF.FF
неприятно и непонятно почему. теперь — ясно.
кроме того — нулевое окно содержит прочитанный каталог карты, и изменение данных там — сказывается на работе коммандера в плохую, очень плохую сторону :)

В общем, держите пока исходники для разбора. при компиляции всё готовое (*.wmf) отправляется в папку wc образа эмуля с помощью чудесной проги от Робуса, стоит лишь указать ей пути в compile.bat
а на выходе — собирается код, выровненный под 512 байт сектора, к которому присоединяется графика.
и получаем плаг.
Для того что-бы WC понял что плаг в системе — нужно поменять в wc.ini строку с plasma.wmf на clock.wmf, учитывая пробелы. точка с запятой является каментом, можно её использовать.



Плаг ей нравится, а это наше с вами увлечение — удивительно и интересно.
Удачи в семейной жизни, ребята. Любите. И кодьте:))


Ссылка на топик о плаге
Скачать плаг

В общем, что там дао говорит?

Дао говорит что плаг состоит из нескольких вещей:
— хидер с описанием — сколько нужно паг для плага, сколько секторов по 512 байт будет загружено в каждую, название и способ запуска плага;
— инклюд с дефайнами, инклюд с вызовом функций WC
— основной код плага.
— основной файл, собирающий всё в пак wmf

особенностью плагов есть то, что вы:
1. не должны использовать свой стек;
2. код отрабатывает с адреса #8000;
3. используйте выражение sjasm «DEVICE» только в основном файле, который будет инклюдить всё;
— sjasm дурной, ошибок компиляции в инклюдах не выдаст, это расстраивает
4. dma для больших перебросок стоит использовать через вызовы api wc, для мелких (например отправка палитры) — я использовал привычные мне методы;
5. установка видеорежимов, видеопаги, чтение клавиатуры и т.п. — только через api wc. в обработчике прерывания всё это будет переустановлено заново
6. поэтому — не используем свой обработчик прерываний, всё необходимое отрабатывает в основном цикле;
7. выход должен быть с восстановлением дефолтного для коммандера экрана.

good bye!

7 комментариев

avatar
надеюсь — вы поняли главную мысль поста.
в плагинной системе главное — ЖЕНИТЬСЯ ;) вперёд к победам! :)
  • VBI
  • +1
avatar
— sjasm дурной, ошибок компиляции в инклюдах не выдаст, это расстраивает
Всё выдаёт. Иначе б бросил давно это дело. Сейчас проект из 59(пока) файлов-сорцов, компилится за раз, из главного файла.
avatar
так у тебя же МАС!
avatar
Mac! — это apple.
MAC — это адрес.
Mc — это шотландец! =)
avatar
Ленивая жопа по имени я всю жизнь искала утилиту типа robimg.exe. Потестирую.
Сначала был найден некий imgcpy.exe, который написан непризнанным гением патчинга мсдоса. Утилита работает, но ровно до тех пор, пока не падает. А падает она от того, что изменили букву в названии копируемого файла, например. Исходники есть (гуглятся), но собрать их равносильно тому, чтоб пропатчить КДЕ под фрибээсди, что бы это не значило. Автору гореть в особом адЪу.
От безысходности я уже собрался взять Chan-ов FatFS, на базе которого сделать утилиту. Вот столечко не хватило.
Значит, потом я нацыкался юзать *.vhd для виртуальных дисков, норм.
  • tsl
  • +1
avatar
Вот и я когда-то искал-искал-искал. Закончилось это тем, что для того что бы отладить простой проект нужно установить 10-ток каких-то утилит и кучу виртуальных драйверов. Вот и я плюнул на это, и написал добавку в asam, который уже семь как генерирует любые файлы в образы. Ибо я не знаю как можно отладить, например, драйвер SD-Card, без перезаписи образа, для чего мне он тогда и нужен был. А потом выяснилось, что Вова постоянно мучается при сборке и тестировании зефира. Пришлось вытащить из asamа ту часть, которая генерирует образы и скомпилировать это в robimg, если, конечно речь идёт именно о моём. Только сразу предупреждаю, образы которые ты получишь не стоит монтировать к виндовсу 7 и выше, но все эмуляторы которые я пробовал прекрасно понимают мои образы. Причина нелюбви винды7 моих образов, в том что таблица ссылки на размеченную область сделана в виде записи нулевого сектора реального HDD, а не с 63-тоего как, например во флеш. То есть полученный образ можешь смело записывать прямо на винчестер. Линукс отлично понимает мои образы без каких-либо вопросов. Если вдруг будут проблемы, то любой копир(NEIRO), может сконвертировать мой образ в нужный тебе. Кстати, Unreal, конечно же твой(TSL), это единственный который не вжирает в себя образ. Львиная доля эмуляторов сходила сума, когда я им подбрасывал образ например в 8 гигабайт, до селе столько памяти приложения на моём компьютере не отъедали никогда.
avatar
Ну вот, что меня удерживало от написания такой утилиты, это поддержка всеразнообразных нюансов фата. Я б делал только на основе чужой либы.
Только зарегистрированные и авторизованные пользователи могут оставлять комментарии.