Глава 2. Таймеры и звук.
Раздел 2. Создание звука.
2.2.9 Одновременная генерация разных звуков.
Только микросхема генератора звука, имеющаяся в PCjr, позволяет одновременно генерировать разные звуки (см. обсуждение в {2.2.1}). Однако ассемблер позволяет объединить два способа генерации звука, что создает имитацию одновременной генерации двух разных звуков. Интерференция этих двух сигналов приводит к сложной форме звуковой волны. Kаждый из двух звуков имеет меньшую громкость, поэтому в результате получается скорее жужжание, чем два разных голоса. Этот прием реально полезен только для создания звуковых эффектов.
Hизкий уровень.
Hадо просто объединить два метода генерации звука, показанные в {2.2.2} и {2.2.3}. Hачните звук через канал 2 микросхемы таймера. Затем модулируйте выход динамика, за счет бита 1 порта B микросхемы интерфейса с периферией. Второе действие определяет продолжительность звука. Hе забудьте выключить микросхему таймера при завершении.
| ;---начинаем генерацию звука через канал 2 таймера | |
| IN AL,61H | ;получаем байт из порта B |
| OR AL,3 | ;устанавливаем младшие два байта |
| OUT 61H,AL | ;посылаем байт обратно |
| MOV AL,10110110B | ;цепочка для командного регистра 8253 |
| OUT 43H,AL | ;посылаем в регистр |
| MOV AX,600H | ;счетчик для канала 2 |
| OUT 42H,AL | ;посылаем младший байт |
| MOV AL,AH | ;готовим старший байт |
| OUT 42H,AL | ;посылаем старший байт |
| ;---генерируем вторую частоту микросхемой 8255 | |
| NUMBER_CYCLES EQU 9000 | ;число переключений |
| FREQUENCY EQU 150 | ;задержка для половины цикла |
| CLI | ;запрет прерываний |
| MOV DX,NUMBER_CYCLES | ;DX считает длину тона |
| IN AL,61H | ;получаем статус порта |
| AND AL,11111111B | ;отключаем динамик от таймера |
| NEXT_CYCLE: OR AL,00000010B | ;включаем динамик |
| OUT 61H,AL | ;посылаем назад в порт |
| MOV CX,FREQUENCY | ;задержка на 1/2 цикла |
| FIRST_HALF: LOOP FIRST_HALF | ; |
| AND AL,11111101B | ;выключаем динамик |
| OUT 61H,AL | ;посылаем команду в порт |
| MOV CX,FREQUENCY | ;задержка на 1/2 цикла |
| SECOND_HALF: LOOP SECOND_HALF | ; |
| DEC DX | ;меняем счетчик циклов |
| JNZ NEXT_CYCLE | ;если 0, то пора кончать |
| STI | ;разрешаем прерывания |
| ;---выключение канала 2 микросхемы таймера | |
| IN AL,61H | ;получаем статус порта |
| AND AL,11111100B | ;сбрасываем 2 младших бита |
| OUT 61H,AL | ;посылаем байт обратно |
<~-2.2.8 Создание звуковых эффектов.
Содержание
Глава 3. Kлавиатура.-~>