Канали MIDI

Як було показано в попередньому розділі, обєкт MidiRead перетворює події в запити до обєктів каналів Тепер прийшов час зайнятися тим, що необхідно обєктам каналів для задоволення цих запитів

Для більшості функцій відтворення не важливо, який обєкт доступний на каналі доти, поки обєкт каналу відповідає на певні повідомлення Клас MidiChannelAbstract визначає можливості обєкта каналу MIDI Більшість цих методів підтримують один тип подій MIDI

Лістинг 2223 Обєкт каналу MIDI

/ / Канал контролює відтворювані зараз ноти class MidiChannelAbstract {

public:

virtual ~MidiChannelAbstract() {}

virtual void StartNote(int pitch, int velocity) = 0 virtual void EndNote(int pitch, int velocity) = 0 virtual void Program(int instrument) = 0

virtual void ChannelAftertouch(int velocity) = 0 virtual void KeyAftertouch(int note, int velocity) = 0 virtual void Mode(int mode, int value) = 0

virtual void PitchBend(int value) = 0

virtual size_t AddSamples(AudioSample *buffer, size_t numberSamples) = 0

}

Для програвання файлів базової або розширеного MIDI бажано вміти заглушати один або кілька каналів Цей простий фіктивний клас успішно реалізує мовчить канал

Лістинг 2223 Обєкт каналу MIDI (продовження)

/ / Заповнювач, який нічого не робить

class MidiChannelSilent: public MidiChannelAbstract {

public:

~MidiChannelSilent() {}

void StartNote(int, int) {} void EndNote(int, int) {} void Program(int) {}

void ChannelAftertouch(int) {} void KeyAftertouch(int, int) {} void Mode(int, int) {}

void PitchBend(int) {}

size_t AddSamples(AudioSample *, size_t) { return 0 }

}

Звичайно, «мовчазні» канали це виняток Звичайний канал повинен відстежувати програються ноти і маніпулювати безліччю інструментів Для спрощення роботи з інструментами я виділив всі аспекти управління ними в єдиний обєкт «карта інструментів», який ми розглянемо пізніше

Лістинг 2223 Обєкт каналу MIDI (продовження)

/ / Канал контролює відтворювані зараз ноти class MidiChannelStandard: public MidiChannelAbstract {private:

float _masterVolume float _channelVolume MidiRead *_midiRead

int _defaultInstrumentBank

int _currentInstrumentBank int _currentInstrumentNumber int _currentTuning

AbstractNote * _note [128] / / Відтворення ноти

int _controllerLong [32] / / 14-бітові контролери int _controllerShort [32] / / 7-бітові контролери int _currentRegisteredParameter

int _registeredParameter [8] / / Зареєстровані

/ / Параметри

void AllNotesOff()

void ResetControllers()

public:

MidiChannelStandard(MidiRead *midiObject, int instrumentBank, float masterVolume)

~MidiChannelStandard()

void StartNote(int pitch, int velocity) void EndNote(int pitch, int velocity) void Program(int instrument)

void ChannelAftertouch(int velocity)

void KeyAftertouch(int note, int velocity)

void Mode(int mode, int value)

void PitchBend(int value)

size_t AddSamples(AudioSample *buffer, size_t numberSamples)

}

Лістинг 2224

MidiChannelStandard:: MidiChannelStandard(MidiRead *midiRead,

int currentBank,

float masterVolume) {

_masterVolume = masterVolume

_midiRead = midiRead

_defaultInstrumentBank = currentBank

_currentInstrumentBank = currentBank

_currentInstrumentNumber = 0

_currentTuning = 0

for (int i=0 i&lt128i++)

_note[i] = 0 ResetControllers()

}

MidiChannelStandard :: ~ MidiChannelStandard () {/ / Очищення

for (int i=0 i&lt128 i++)

if(_note[i]) {

delete _note[i]

_note[i] = 0

}

}

Одна з відмінностей простого електронного синтезатора від фортепіано полягає в тому, що останнє видає різні звуки залежно від того, наскільки швидко ви відпускаєте клавішу Протокол MIDI реалізує подібна поведінка через швидкість, яка визначає, як швидко ви натискаєте або відпускаєте клавішу Що стосується подій включення нот, то більш висока швидкість виражається в більш гучному звучанні ноти (часто також відбувається загальна зміна звукової картини) Для подій вимикання нот більш висока швидкість означає більш швидке відпускання клавіші, а отже, меншу тривалість звучання

Лістинг 2224 (продовження)

void MidiChannelStandard::Program(int instrument) {

_currentInstrumentNumber = instrument

_currentInstrumentBank = _controllerLong[0]

}

void MidiChannelStandard::StartNote(int note, int velocity) {

if (_note[note]) delete _note[note]

/ / Вибір відповідного інструменту

AbstractInstrument *instr =

_midiRead-&gtInstrumentMap()-

&gtInstrument(_currentInstrumentBank,

_currentInstrumentNumber,note)

/ / Отримуємо настройку для цієї ноти float pitch = _midiRead-> TuningMap () –

&gtTuning(_currentTuning,note)

_note[note] = instr-&gtNewNote(pitch, velocity*_channelVolume*_masterVolume)

}

void MidiChannelStandard::EndNote(int note, int velocity) {

if (_note [note] )

_note[note]-&gtEndNote(velocity/1270)

}

void MidiChannelStandard::AllNotesOff() {

for (int i=0 i&lt128i++)

if(_note[i])

_note[i]-&gtEndNote(00)

}

Механізми aftertouch і Pitch Wheel

B цій частині особливо виразно проявляється клавіатурне спадщина MIDI Вчинені клавіатури дозволяють управляти звучанням ноти, яка вже програється Ця можливість здійснюється шляхом використання датчика тиску, розташованого під клавішею Змінюючи тиск, зване також

aftertouch (післяторкання),музикант змінює звучання Зазвичай таке утримання клавіші змінює параметр вібрато, але, в залежності від клавіатури, можуть змінюватися і інші характеристики звуку Багато електронні клавіатури також підтримують повноціннеколесо висоти тону (pitch wheel)звуку, яке дозволяє відхиляти висоту тону для всіх нот Механізм управління висотою надає дію на весь канал, а не на одну ноту Крім того, використовуються два повідомлення aftertouch: одне для окремої ноти, інше для цілого каналу

Лістинг 2224 (продовження)

/ / Я поки не працюю з aftertouch і pitch wheel

void MidiChannelStandard::KeyAftertouch(int note, int velocity) {

cerr &lt&lt &quotKey Aftertouch: &quot &lt&lt note &lt&lt &quot velocity: &quot &lt&lt

velocity &lt&lt &quot\n"

}

void MidiChannelStandard::ChannelAftertouch(int velocity) {

cerr &lt&lt &quotChannel Aftertouch: velocity: &quot &lt&lt velocity &lt&lt &quot\n"

}

void MidiChannelStandard::PitchBend(int) {

}

Відтворення каналу здійснюється шляхом програвання всіх актив-

них в поточний момент часу нот

Лістинг 2224 (продовження)

size_t MidiChannelStandard::AddSamples(AudioSample *buffer, size_t

numberSamples) {

for(int i=0 i&lt 128 i++) {

if (_note[i]) {

size_t samplesRead =

_note[i]-&gtAddSamples(buffer,numberSamples)

if (samplesRead

/ / Ноти закінчено

delete _note[i]

_note[i] = 0

}

}

}

return numberSamples

}

Контролери та режими

Події з кодами від 0xB0 до 0xBF використовуються для зміни різних параметрів Ці параметри розділені на чотири групи: 7-бітові елементи управління (контролери) постійної дії, 14-бітові елементи управління постійної дії, параметри і канальні режими

7-бітові елементи управління

Повідомлення зміни управління містить два байти даних Перший визна-

ляє, що потрібно поміняти (Номер елемента управління) другий визначає нове

значення Як і для всіх байтів даних, значення обмежені сімю битами B більшості випадків цього більш ніж достатньо B стандарті MIDI для цих цілей резервуються елементи управління з 64-го по 95-й (0x40 0x5F)

B табл 227 наведена зведена інформація з 7-бітним елементам управ-

лення Зауважимо, що деякі з них використовують менше 128 значень Наприклад, елементи управління легато і портаменто або активують, або дезактивують відповідний ефект Для таких елементів управління значення менші 64 є дезактивирующими, а значення більші або рівні 64 трактуються як активуючі Це справедливо для будь-якого елемента управління з невеликим діапазоном 0 завжди являє мінімальне значення,

127 максимальне інші значення відповідним чином Інтерпен-

люються

Таблиця 227 Семібітние контролери

Повідомлення Опис

(Шістнадцяткове)

Bc 40 vv                                   Педаль демпфера (вкл / викл) Bc 41 vv                                   Портаменто (вкл / викл)

Bc 42 vv                                   Сустенуто

Bc 43 vv                                   Ліва педаль

Bc 44 vv                                   Педаль легато (вкл / викл) Bc 45 vv                                   Пауза 2

Bc 46 vv                                   Елемент управління звуком 1 (варіювання звуку)

Bc 47 vv                                   Елемент управління звуком 2 (інтенсивність тембру / гармонік) Bc 48 vv                                   Елемент управління звуком 3 (час загасання)

Bc 49 vv                                   Елемент управління звуком 4 (час атаки) Bc 4A vv                                   Елемент управління звуком 5 (яскравість)

Bc 4B vv                                   Елемент управління звуком 6 (немає визначення) Bc 4C vv                                  Елемент управління звуком 7 (немає визначення) Bc 4D vv                                  Елемент управління звуком 8 (немає визначення) Bc 4E vv                                   Елемент управління звуком 9 (немає визначення) Bc 4F vv                                   Елемент управління звуком 10 (немає визначення) Bc 50 vv                                   Елемент управління загального призначення 5

Bc 51 vv                                   Елемент управління загального призначення 6

Bc 52 vv                                   Елемент управління загального призначення 7

Bc 53 vv                                   Елемент управління загального призначення 8

Bc 54 vv                                   Елемент управління портаменто

Bc 5B vv                                   Глибина ефекту 1

Bc 5C vv                                   Глибина ефекту 2

Bc 5D vv                                  Глибина ефекту 3

Bc 5E vv                                   Глибина ефекту 4

Bc 5F vv                                   Глибина ефекту 5

14-бітові контролери

B деяких випадках семи біт виявляється недостатньо, тому стандарт MIDI також описує 32 четирнадцатібітних контролера Для такого елемента управління потрібні два номери: один для старших семи біт, другий для молодших

Номери елементів управління з 0 по 31 (0x00 0x1F) використовуються для старших семи біт 14-бітних елементів управління, а номери з 32 по 63 (0x20 –

0x3F) для молодших семи біт B табл 228 перераховуються певні в на-

варте час 14-бітові елементи управління Так як дві половини задаються

незалежно, вам слід звернути увагу на взаємодію між ними: зокрема, коли змінюються старші сім біт, молодші неявно встановлюються в нуль При створенні файлів MIDI завжди слід спочатку задавати значення старших семи біт

Параметри

Деякі елементи управління працюють трохи інакше по параметричного механізму Замість безпосередньої вказівки значення елемента керування спочатку вибирається відповідний параметр шляхом посилки його 14-бітного коду (використовуються два повідомлення для передачі старшої і молодшої сімки бітів),

Таблиця 228 Четирнадцатібітние контролери

Контролер для

старших семи біт

Контролер для

молодших семи біт

Опис

0 (0x00)

32 (0x20)

Вибір банку

1 (0x01)

33 (0x21)

Колесо або важіль модуляції

2 (0x02)

34 (0x22)

Елемент управління повітрям

3 (0x03)

35 (0x23)

Не визначено

4 (0x04)

5 (0x05)

36 (0x24)

37 (0x25)

Елемент управління ногою

Період портаменто

6 (0x06)

38 (0x26)

Введення даних

7 (0x07)

8 (0x08)

39 (0x27)

40 (0x28)

Гучність каналу

Баланс

9 (0x09)

41 (0x29)

Не визначено

10 (0x0A)

42 (0x2A)

Панорамування

11 (0x0B)

43 (0x2B)

Елемент управління експресією

12 (0x0C)

44 (0x2C)

Управління ефектами 1

13 (0x0D)

45 (0x2D)

Управління ефектами 2

14 (0x0E)

46 (0x2E)

Не визначено

15 (0x0F)

47 (0x2F)

Не визначено

16 (0x10)

48 (0x30)

Елемент управління загального призначення 1

17 (0x11)

49 (0x31)

Елемент управління загального призначення 2

18 (0x12)

50 (0x32)

Елемент управління загального призначення 3

20 (0x13)

51 (0x33)

Елемент управління загального призначення 4

20-31

52-63

Не визначено

а потім цей параметр змінюється Зауважимо, що всі параметри являють собою

14-бітові значення B стандарті описано до 16384 зареєстрованих (registered) параметрів і, крім того, 16 384незареєстрованих (non-registered)Зареєстровані параметри є офіційною частиною стандарту, незарегістріро-

ванні можуть використовуватися ким завгодно в будь-яких цілях Як випливає з табл 229,

для параметричного механізму необхідно всього 8 номерів елементів управління B табл 2210 перераховані основні зареєстровані на даний час параметри Зауважте, що параметри 1 і 2 представляють одне 28-бітове значення настройки

Щоб подивитися, як працює цей механізм, задамо для параметра 2 (гру-

бая настройка) каналу 3 значення 0x12BC такою послідовністю байтів:

 ‰  0xB2 0x64 0x00 Ð ² Ñ <Ð ± Ð ¾ Ñ € Ð · Ð ° Ñ € ÐμÐ ³ Ð ¸ Ñ Ñ, Ñ € Ð ¸ Ñ € Ð ¾ Ð ² Ð ° Ð ½ Ð ½ Ð ¾ Ð ³ Ð ¾ Ð ¿Ð ° Ñ € Ð ° Ð ¼ ÐμÑ, Ñ € Ð °, Ñ Ñ, Ð ° Ñ € ÑÐ ¸ Ðμ 7Ð ± Ð ¸ Ñ, Ð º Ð ¾ -

торого рівні 0

 ‰   0x65 0x002 Ð ¿Ð ¾ Ð »Ð ½ Ñ <Ð ¹ Ð ² Ñ <Ð ± Ð ¾ Ñ € Ð · Ð ° Ñ € ÐμÐ ³ Ð ¸ Ñ Ñ, Ñ € Ð ¸ Ñ € Ð ¾ Ð ² Ð ° Ð ½ Ð ½ Ð ¾ Ð ³ Ð ¾ Ð ¿Ð ° Ñ € Ð ° Ð ¼ ÐμÑ, Ñ € Ð ° 2 (Ð ¾ Ð ± Ñ € Ð ° Ñ, Ð ¸ Ñ, Ðμ

увагу на безперервний статус неявно використовується значення 0xB2)

 ‰   0x06 0x25 Ð ¿Ð ¾ Ñ Ð »Ð ° Ñ, ÑŒ Ñ Ñ, Ð ° Ñ € ÑÐ ¸ Ðμ 7 Ð ± Ð ¸ Ñ, Ð ½ Ð ¾ Ð ² Ð ¾ Ð ³ Ð ¾ Ð · Ð ½ Ð ° Ñ ‡ ÐμÐ ½ Ð ¸ Ñ Ð ³ Ñ € уР± Ð ¾ Ð ¹ Ð ½ Ð ° Ñ ​​Ñ, Ñ € Ð ¾ Ð ¹ Ð º Ð ¸

 ‰   0x06 0x3C Р¿Ð ¾ Ñ Ð »Ð ° Ñ, ÑŒ Ð ¼ л Ð ° ÐÑÐ ¸ Ðμ 7 Ð ± Ð ¸ Ñ, Ð ½ Ð ¾ Ð ² Ð ¾ Ð ³ Ð ¾ Ð · Ð ½ Ð ° Ñ ‡ ÐμÐ ½ Ð ¸ Ñ Ð ³ Ñ € уР± Ð ¾ Ð ¹ Ð ½ Ð ° Ñ Ñ, Ñ € Ð ¾ Ð ¹ Ð º Ð ¸

Режими каналів

Крім контролерів, існує вісім сообщенін режиму каналу (Channel mode) Номер каналу в цьому випадку має зовсім інше значення Згадаймо,

Таблиця 229 Повідомлення контролерів для зміни параметрів

Повідомлення Опис

(Шістнадцяткове)

Bc 06 vv                                   Елемент даних: задає старші 7 біт поточного параметра

Bc 26 vv                                   Елемент даних: задає молодші 7 біт поточного параметра

Bc 60 vv                                    Інкремент даних: збільшує на одиницю поточний параметр Bc 61 vv                                   Декремент даних: зменшує на одиницю поточний параметр Bc 62 vv                                   Вибір незареєстрованого параметра (старші 7 біт,

молодші 7 біт рівні 0)

Bc 63 vv                                   Вибір незареєстрованого параметра (молодші 7 біт) Bc 64 vv                                   Вибір зареєстрованого параметра (старші 7 біт,

молодші 7 біт рівні 0)

Bc 65 vv                                    Вибір зареєстрованого параметра (молодші 7 біт)

Таблиця 2210 Зареєстровані параметри

Параметр Опис

0 Чутливість механізму варіювання висоти

1 Точна настройка

2 Груба настройка

3 Вибір програми настройки

4 Вибір банку настройки

що звичайна середу функціонування MIDI являє собою безліч повязаних один з одним пристроїв Кожен пристрій може працювати з будь-яким підмножиною з 16 каналів Для спрощення рішення певних завдань кожен пристрій також має базовий канал (basic channel)

Повідомлення режиму каналу, що посилаються в цей базовий канал, змінюють режим роботи всього пристрою Якщо який-небудь один синтезатор працює з усіма каналами, базовим найчастіше є канал 1

B випадку з синтезатором, реалізованому на програмному рівні (приблизно так як продемонстровано в цьому розділі), залишається неясним питання інтерпретації базового каналу Програмний синтезатор можна розглядати як один пристрій, працююче з усіма 16 каналами, або як 16 віртуальних пристроїв, кожне з яких працює з одним каналом B програмі, описаної в цьому розділі, я використовував останню інтерпретацію B табл 2211 приведена загальна інформація за повідомленнями режиму каналу

Режим omni (Omni mode) визначає, чи буде заданий бокс працювати з усіма каналами (активний omni) або тільки зі своїм базовим каналом (пасивний omni)Монофоніческійрежім(Mono mode) іполіфоніческійрежім(Poly mode) визначають спосіб обробки паралельних нот одним каналом B першому випадку кожен канал відтворює в будь-який момент часу одну ноту якщо активизирующее ноту подія отримано до відключення попередньої ноти, то програється в поточний момент часу нота змінює висоту Це варіант легато Зауважимо, що відправник все одно повинен послати дезактивують подія для попередньої ноти Основне правило MIDI полягає в тому, що за будь-яким активирующим ноту подією має рано чи пізно слідувати відповідне дезактивують подія B поліфонічному режимі кожен канал може відтворювати стільки нот, скільки зуміє

Таблиця 2211 Повідомлення режиму каналу

Повідомлення Опис

(Шістнадцяткове)

Bc F8 00 Вимкнути весь звук: вимкнути всі ноти, луна пауз і тд Bc F9 00 Повторно ініціалізувати всі елементи управління

(Ігнорується в режимі omni)

Bc FA vv                                    Місцеве управління

Bc FB 00 Вимкнути всі ноти

Bc FC 00 Вимкнути режим omni, а також всі ноти

Bc FD 00 Включити omni (також вимкнути всі ноти)

Bc FE vv                                    Включити монорежим / відключити поліфонію (також вимкнути всі ноти): vv кількість каналів, які, починаючи з базового,

повинні використовувати монорежим

Bc FF 00 Включити поліфонію / відключити монорежим (також вимкнути всі ноти)

Реалізація

Лістинг 2224 (продовження)

void MidiChannelStandard::Mode(int mode, int value) {

/ / 14-бітові контролери

if (mode <32) / / 0-31 старші біти (MSB).

_controllerLong[mode] = value &lt&lt 7

if ((mode> = 32) && (mode <64)) / / Молодші біти (LSB).

_controllerLong[mode-32] =

(_controllerLong[mode-32] &amp 0x3F80) + value

/ / 7-бітові контролери

if ((mode> = 64) && (mode <96)) / / однобайтное контролери.

_controllerShort[mode-64] = value

/ / Налаштування параметрів

if (mode == 96) {/ / 96 збільшення даних

_registeredParameter[_currentRegisteredParameter]++

_controllerLong[6] =

_registeredParameter[_currentRegisteredParameter]

}

if (mode == 97) {/ / 97 зменшення даних

_registeredParameter[_currentRegisteredParameter]–

_controllerLong[6] =

_registeredParameter[_currentRegisteredParameter]

}

/ / 98 не реєструвалися параметри LSB

/ / 99 не реєструвалися параметри MSB

if (mode == 100) {/ / Зареєстровані параметри LSB

_currentRegisteredParameter = (_currentRegisteredParameter &amp 0x3F80)+(value)

_controllerLong[6] =

_registeredParameter [_currentRegisteredParameter]

}

if (mode == 101) {/ / Зареєстровані параметри MSB

_currentRegisteredParameter = value&lt&lt7

_controllerLong[6] =

_registeredParameter[_currentRegisteredParameter]

}

/**************************************/

/ * Повідомлення режимів каналу (120-127) * /

/**************************************/

/ / 120 звук вимкнений повністю

/ / 121 перезапустити всі контролери

if (mode == 121) ResetControllers()

/ / 123 всі ноти відключені (124-127 –

/ / Те ж саме)

if (mode &gt= 123) AllNotesOff()

/ / 124 режим omni відключений

/ / 125 режим omni включений

/ / 126 монофонический режим включений

/ / (Одна нота на канал)

/ / 127 поліфонічний режим

/ / Включений (кілька нот

/ / На канал)

}

void MidiChannelStandard::ResetControllers() {

int i

for(i=0i&lt32i++) {

_controllerLong[i] = 0

_controllerShort[i] = 0

}

for(i=0i&lt8i++) {

_registeredParameter[i] = 0

}

_controllerLong[0] = _defaultInstrumentBank

_controllerLong [7] = 100 << 7; / / Гучність за замовчуванням.

_controllerLong [8] = 0x2000 / / Контроль балансу: 1/2 =

/ / Однаковий рівень

/ / Вихідних сигналів

_controllerLong [10] = 0x2000 / / Контроль панорами: 1/2 =

/ / Центрирована

_controllerLong [ll] = 0x2000 / / Середня вираз

_currentRegisteredParameter = 0

_registeredParameter[0] = 0

//

Зсув висоти тону

//

за замовчуванням:

//

плюс-мінус 2 півтони

_registeredParameter[1] = 0x2000

//

Тонка настройка

//

за замовчуванням

_registeredParameter[2] = 0x2000

//

Груба настройка

//

за замовчуванням

/ / Оновлюємо ряд змішаних змінних

_channelVolume = _controllerLong[7]/163840

}

Налаштування нот в MIDI

Нещодавно до стандарту MIDI було зроблено доповнення: тепер передбачена можливість перевизначати значення висоти нотMIDI  Для реалізації цього в моєму програвачі MIDI є єдинакарта настройки,яка перетворює нотні значення в частоти

B вихідної версії карта настройки використовує рівномірно темперований шкалу, в якій Ля 440 Гц це нота 69 (Специфікація General MIDI вимагає, щоб середнє До відповідало ноті 60, що еквівалентно нашому варіанту)

Лістинг 2225 Карта налаштування MIDI

class MidiTuningMap {

public:

float Tuning(int, int note) {

return 4400*pow(20,(note-69)/120)

}

}

Джерело: Кінтцель Т Керівництво програміста по роботі зі звуком = A Programmers Guide to Sound: Пер з англ М: ДМК Пресс, 2000 432 с, іл (Серія «Для програмістів»)

Схожі статті:


Сподобалася стаття? Ви можете залишити відгук або підписатися на RSS , щоб автоматично отримувати інформацію про нові статтях.

Коментарів поки що немає.

Ваш отзыв

Поділ на параграфи відбувається автоматично, адреса електронної пошти ніколи не буде опублікований, допустимий HTML: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <s> <strike> <strong>

*

*