Как написать игру для ZX Spectrum на ассемблере


         

ПОЛУЧЕНИЕ ЧИСТОГО ТОНА - часть 3


Прежде чем обратиться к данной процедуре выпишем числа, полученные с нашим импровизированным «редактором» при заданном темпе, равном 150, в виде блока двухбайтовых данных, который завершим числом 0 (тоже двухбайтовым):

DATMEL DEFW 39,1086,35,1223,33,1297 DEFW 29,1460,66,1297,78,1086 DEFW 39,2202,49,1742,105,1642 DEFW 0 ;маркер конца блока данных

Теперь можно вызвать процедуру MELODY, например, таким образом:

ORG 60000 ENT $ LD HL,DATMEL CALL MELODY RET

Существует и другой способ извлечения звуков, при котором все необходимые расчеты выполняются в самой программе. Хотя он и несколько сложнее только что описанного, но может показаться вам более привлекательным. Во всяком случае он более привычен, так как исходными данными при этом являются те же числа, что и параметры оператора BEEP. Подпрограмма, расположенная по адресу 1016, сама выполняет приведенные выше вычисления и обращается к процедуре вывода звука 949, а значения длительности и высоты звука передаются ей через стек калькулятора:

LD A,1 ;загружаем в аккумулятор значение ; длительности звучания (1 секунда). CALL 11560 ;содержимое аккумулятора заносим ; в стек калькулятора. LD A,12 ;нота ДО второй октавы CALL 11560 ;посылаем в стек калькулятора CALL 1016 ;вызываем процедуру извлечения звука RET

Этот метод хорош всем, за исключением одной «мелочи» - числа, записываемые в аккумулятор могут быть только целыми и не отрицательными. Чтобы исправить этот недостаток, можно условиться, что длительности будут задаваться не в секундах, а в сотых долях секунды, а значение высоты звука будем интерпретировать как число со знаком. Такой подход позволит получать продолжительность звучания нот примерно до двух с половиной секунд, что в большинстве случаев вполне достаточно; диапазон звуков останется таким же, как и в Бейсике: от -60 до +68. Параметры для этой подпрограммы будем задавать в регистрах B (длительность в сотых долях секунды) и C (высота в полутонах):

BEPER PUSH BC LD A,B ;берем в аккумулятор первый параметр CALL 11560 ;заносим его в стек калькулятора LD A,100 CALL 11560 ;помещаем в стек число 100 RST 40 DEFB 5,56 ;выполняем деление POP BC LD A,C ;берем второй параметр AND A JP M,BEPER1 ;если отрицательный, переходим на BEPER1 CALL 11560 ; иначе помещаем в стек без изменений JP 1016 ; и извлекаем звук BEPER1 NEG ;получаем абсолютное значение CALL 11560 ;отправляем в стек RST 40 DEFB 27,56 ;меняем знак JP 1016 ; и извлекаем звук




Содержание  Назад  Вперед