vs1003 как миди синтезатор
- Войдите на сайт для отправки комментариев
Ср, 04/07/2018 - 13:45
Достался модуль нахаляву (больше года работал оповещателем на заводе) на микросхеме vs1003. Файлы mp3 поигрался, послушал, но теперь хочу, чтоб он, как миди синтезатор заиграл (благо миди-клава валяется давно). Для пробы написал такой скеч
#include <SPI.h>
#include <arduino.h>
#include <MusicPlayer.h>
/*
* GND - GND
* XDCS - D6
* DREQ - D7
* XRES - D8
* XCS - D9
* SCLK - D13
* SI - D11
* SO - D12
* GND - GND
* 5V - 5V
*/
void setup () {
// initiate SPI
SPI.begin();
// initiate a serial port at 9600
Serial.begin(9600);
// initiate VS1003 for MIDI
player.beginInMidiFmt(); //Инициализировать аппаратное обеспечение и установить режим MIDI по умолчанию.
player.midiWriteData(0xB0, 0x07, 120); //установить громкость
player.midiDemoPlayer ();
}
void loop() {
// играть ноты от F#-(30) до F#-(90):
for (int note = 30; note < 90; note ++) {
player.midiNoteOn(1,note,127);
delay(50);
player.midiNoteOff(1,note,127);
delay(50);
}
}
Но эта сволочь молчит, как партизан, ни звука. Может кто сталкивался и смог победить?
Насчет vs1003 не знаю, могу сказать только насчет vs1053. Насколько они совместимы - не интересовался.
1. Проигрывание MIDI-файлов и реалтаймовое MIDI - это не одно и то же. На просторах И-нета можно найти программку - в уже откомпилированном виде занимает байт 20-30, как раз она переводит чип в режим реалтаймового MIDI. Для чего ее сперва нужно загружить в DSP.
2. Процессор 1053 - 16-разрядный. Соответственно, на вход ему надо подавать не однобайтные, а двухбайтные коды. (насколько это критично - не знаю, вероятно player.midiNote* так и делает, но хорошо бы проверить.)
3. В названии библиотеки не фигурирует "VS1003", есть ли уверенность, что библиотека именно для этого чипа?
Насколько я понял из даташитов этих процессоров 53, отличается от 03 расширенной и улучшенной библиотекой инструментов. На сайе http://www.vlsi.fi/en/products/vs1003.html для обоих кристаллов ссылаются на одни и те же примеры. А при инициализации командой player.beginInMidiFmt(); библиотека vs10xx.h подгружает в проц вот это:
//software patch for MIDI Play const unsigned short gVS1053_MIDI_Patch[28]={ /*if you don't let GPIO1 = H,please send this patch by spi*/ 0x0007, 0x0001, 0x8050, 0x0006, 0x0014, 0x0030, 0x0715, 0xb080, /* 0 */ 0x3400, 0x0007, 0x9255, 0x3d00, 0x0024, 0x0030, 0x0295, 0x6890, /* 8 */ 0x3400, 0x0030, 0x0495, 0x3d00, 0x0024, 0x2908, 0x4d40, 0x0030, /* 10 */ 0x0200, 0x000a, 0x0001, 0x0050, };чисто для vs1003 такую я не нашел, потому и обратился сюда.
Да, я использую этот же код, только добавил в него "разгон" процессора примерно до 60 МГц.
Правда, беглое знакомство с приведенной Вами ссылкой на этот код меня нее вывело.
Подробно разбираться с vs1003 у меня сейчас ни времени, ни желания нет. Единственное, чем могу поспособствовать, либо проверить тот код, что Вы загружаете в vs1003 в свой 1053, либо, наоборот, привести код, который работает у меня на 1053. Но это в лучшем случае сегодня вечером.
И, кстати, в каком виде у Вас само устройство? Насколько я помню, ему нужно два разных напряжения питания.
У меня сейчас в доступности примерно такой:
И с него нельзя снимать сигнал относительно общего провода - там специально есть контакт, предназначенный для использования в качестве общего с наушниками, но не соединенный с GND.
Если можно, то и мой проверить, и свой привести. Чтобы определится: ошибка в коде или модуле
е.
Ваш код проверить не могу ввиду отсутствия у меня библиотеки "MusicPlayer", публикую тот, что у меня работает (сразу прошу прощения, в коде много лишнего - чистить не стал)
MP3_Shield_VS1053b.ino
VS1053B_MIDI.h
VS1053B_MIDI.cpp
#include "VS1053B_MIDI.h" #include <SPI.h> //#include "arh_2560.h" SPISettings VS1053B_START(VS_START_SPEED, MSBFIRST, SPI_MODE0); //SPISettings VS1053B_HiFreq(VS_START_SPEED, MSBFIRST, SPI_MODE0); SPISettings VS1053B_HiFreq(VS_SPEED, MSBFIRST, SPI_MODE0); byte pinRead(byte pin) {return digitalRead(pin);} void pinOutHigh(byte pin) {digitalWrite(pin, HIGH);} void pinOutLow(byte pin) {digitalWrite(pin, LOW);} void pinModeOut(byte pin) {pinMode(pin, OUTPUT);} void pinModeIn(byte pin) {pinMode(pin, INPUT);} //Write to VS10xx register //SCI: Data transfers are always 16bit. When a new SCI operation comes in DREQ goes low. We then have to wait for DREQ to go high again. //XCS should be low for the full duration of operation. void VSWriteRegister(unsigned char addressbyte, unsigned char highbyte, unsigned char lowbyte){ while(!pinRead(VS_DREQ)) ; //Wait for DREQ to go high indicating IC is available SPI.beginTransaction (VS1053B_START); pinOutLow(VS_XCS); //Select control //SCI consists of instruction byte, address byte, and 16-bit data word. SPI.transfer(0x02); //Write instruction SPI.transfer(addressbyte); SPI.transfer(highbyte); SPI.transfer(lowbyte); while(!pinRead(VS_DREQ)) ; //Wait for DREQ to go high indicating command is complete pinOutHigh(VS_XCS); //Deselect Control SPI.endTransaction (); } // Plugin to put VS10XX into realtime MIDI mode // Originally from http://www.vlsi.fi/fileadmin/software/VS10XX/vs1053b-rtmidistart.zip // Permission to reproduce here granted by VLSI solution. const PROGMEM unsigned short sVS1053b_Realtime_MIDI_Plugin[] = { /* [28] Compressed plugin */ 0x0007, 0x0001, 0x8050, 0x0006, 0x0014, 0x0030, 0x0715, 0xb080, /* 0 */ 0x3400, 0x0007, 0x9255, 0x3d00, 0x0024, 0x0030, 0x0295, 0x6890, /* 8 */ 0x3400, 0x0030, 0x0495, 0x3d00, 0x0024, 0x2908, 0x4d40, 0x0030, /* 10 */ 0x0200, 0x000a, 0x0001, 0x0050, 0x0003, 0x0001, 0xd800 // добавлена команда увел.частоты: d800->r3 (x4.5+1.5) }; // 0x9800: x3.5+1.5, 0xa00: x4.0+0.0, 0xb800: x4.0+1.5, 0xc00: x4.5+0.0, 0xe00: x5.0+0.0 void VSLoadUserCode(void) { int i = 0; while (i<sizeof(sVS1053b_Realtime_MIDI_Plugin)/sizeof(sVS1053b_Realtime_MIDI_Plugin[0])) { unsigned short addr, n, val; // pgm_read_word_near(&glideStepArray[glide]) addr = pgm_read_word_near(&sVS1053b_Realtime_MIDI_Plugin[i++]); n = pgm_read_word_near(&sVS1053b_Realtime_MIDI_Plugin[i++]); while (n--) { val = pgm_read_word_near(&sVS1053b_Realtime_MIDI_Plugin[i++]); VSWriteRegister(addr, val >> 8, val & 0xFF); } } } //Sends a MIDI command/data. Doesn't check to see that cmd is greater than 127, or that data values are less than 127 void talkMIDI(byte cmd, byte data1, byte data2) { while (!pinRead(VS_DREQ)); // Wait for chip to be ready (Unlikely to be an issue with real time MIDI) SPI.beginTransaction (VS1053B_HiFreq); pinOutLow(VS_XDCS); SPI.transfer(0); SPI.transfer(cmd); // sendMIDI(cmd); //Some commands only have one data byte. All cmds less than 0xBn have 2 data bytes //(sort of: http://253.ccarh.org/handout/midiprotocol/) if( (cmd & 0xF0) <= 0xB0 || (cmd & 0xF0) >= 0xE0) { SPI.transfer(0); SPI.transfer(data1); SPI.transfer(0); SPI.transfer(data2); } else { SPI.transfer(0); SPI.transfer(data1); } pinOutHigh(VS_XDCS); SPI.endTransaction (); } void VS1053B_setup() { pinOutHigh(VS_XCS); //Deselect Control pinModeOut(VS_XCS); pinOutHigh(VS_XDCS); //Deselect Data pinModeOut(VS_XDCS); pinOutLow(VS_RESET); //Put VS1053 into hardware reset pinModeOut(VS_RESET); pinModeIn(VS_DREQ); //Setup SPI for VS1053 // pinMode(VS_SPI_CS, OUTPUT); //Pin 10 must be set as an output for the SPI communication to work SPI.begin(); //// SPI.setBitOrder(MSBFIRST); //// SPI.setDataMode(SPI_MODE0); //From page 12 of datasheet, max SCI reads are CLKI/7. Input clock is 12.288MHz. //Internal clock multiplier is 1.0x after power up. //Therefore, max SPI speed is 1.75MHz. We will use 1MHz to be safe. //// SPI.setClockDivider(SPI_CLOCK_DIV16); //Set SPI bus speed to 1MHz (16MHz / 16 = 1MHz) // SPI.setClockDivider(SPI_CLOCK_DIV64); //Set SPI bus speed to 500kHz (16MHz / 32 = 500kHz) SPI.transfer(0xFF); //Throw a dummy byte at the bus delayMicroseconds(1); pinOutHigh(VS_RESET); //Bring up VS1053 VSLoadUserCode(); // if USE_PATCH_INIT // VSWriteRegister(3, 0xb8, 0x00); // register, lobyte, hibyte: 98: x3.5+1.5, b8: x4+1.5, a0: x4+0 delay(1000); // (4) // VS1053B.SPISettings(VS_SPEED, MSBFIRST, SPI_MODE0); talkMIDI(0xB0, 0x79, 127); // Reset All Controllers talkMIDI(0xB0, 0x7B, 0); // All Notes Off talkMIDI(0xB0, 0x5B, 0x41); // External effects depth talkMIDI(0xB0, 0x5D, 0); // Chorus depth talkMIDI(0xB0, 0x40, 0); // Sustain pedal talkMIDI(0xB0, 0x00, 0); // Bank select talkMIDI(0xB0, 0x01, 0); // Modulation Wheel talkMIDI(0xB0, 0x0A, 0x37); // Pan // talkMIDI(0xC0, 0x38, 0); // Program number talkMIDI(0xE0, 0x00, 0x40); // Pitch Wheel // talkMIDI(0xB4, 0x40, 0); // // Status Index Argument Description //========================================================== // Bn 78 00 All Sounds Off // Bn 79 7F Reset All Controllers // Bn 7A 7F on/00 off Local Control On/Off // Bn 7B 00 All Notes Off // Bn 7C 00 Omni Mode Off (All Notes Off) // Bn 7D 00 Omni Mode On (All Notes Off) // Bn 7E channels Mono Mode On (Poly Mode Off) // Bn 7F 00 Poly Mode On (Mono Mode Off) // Controller # Function Controller # Function // 46 Sound variation 5B External effects depth // 47 Timbre/harmonic content 5C Tremolo depth // 48 Release time 5D Chorus depth // 49 Attack time 5E Detune depth // 4A Brightness 5F Phase depth // 4B-4F No default talkMIDI(0xB0, 0x07, 0x7F); // Main Volume talkMIDI(0xB0, 0, 0x00); //Default bank GM1 // talkMIDI(0xB0, 0, 0x78); //Bank select drums } //Send a MIDI note-on message. Like pressing a piano key //channel ranges from 0-15 void noteOn(byte channel, byte note, byte attack_velocity) { talkMIDI( (0x90 | channel), note, attack_velocity); } //Send a MIDI note-off message. Like releasing a piano key void noteOff(byte channel, byte note, byte release_velocity) { talkMIDI( (0x80 | channel), note, release_velocity); } void sendMIDI(byte data) { while (!pinRead(VS_DREQ)); // Wait for chip to be ready (Unlikely to be an issue with real time MIDI) SPI.beginTransaction (VS1053B_HiFreq); pinOutLow(VS_XDCS); SPI.transfer(0); SPI.transfer(data); pinOutHigh(VS_XDCS); SPI.endTransaction (); }Библиотека для vs10xx, которую использую я:https://github.com/Seeed-Studio/Music_Shield . Вашу смогу попробовать только в воскресенье. Спасибо.
Глянул вашу библиотеку: 3 и 4 не подключены, подходит только вариант с плагином SPI. Или подпояться к ножкам 33 и 34.
Я уже не помню, какие ножки за что отвечают, но если про последовательный порт, то он не разведен на самом шилде (также и на модуле, который показан ниже). Т.е. вариант только один - через SPI.
Начинаю думать что мой модуль вообще не способен воспроизводить MIDI. Перепробовал кучу вариантов, ни один не произвел ни звука.
Подскажите, пожалуйста, куда подключить выход МИДИ клавы? К ардуино же? Если клава не ЮСБ, то видимо через отпрон прямо на RX? Но к коде я вообще не вижу чтения Uart....
А ви с какой целью интересуетесь?
В смысле?)) Тоже хочу сделать такое как тс..
Ну, тогда вопросы к ТС.