abc941で紹介したように、「秀丸エディッタ」でSD-PAD15による「テキスト入力」ができなかった。VisualStudioCodeではSD-PAD15の全機能が使えるが、補完機能がデフォルトで働き、邪魔になる場合がある(Editor:QuiickSuggestionsでON/OFFの設定が可能ですが・・)。
そこで、無料の日本語エディッタである「サクラエディッタ」を使ってみた。なお、サクラエディッタの動作環境はwindows10までですが、v2.4.2はwindows11でも動作し、今のところ不具合はありません。そして、SD-PAD15も問題なく使えます。サクラエディッタの詳細は以下のページを参照、
M5_AtomS3R(AtomS3では内部リソースと競合する可能性あり)とAtomicスピーカーベースで、Atomic SPK Base Arduino Tutorialを参考に、スピーカー動作テストとSDカードに保存されたWAVファイルの演奏を試みた。
【動作テストとトラブル】
参考ページの「BasicUsage(M5Unified)」で動作を確認したところ、spk_cnfの設定でエラーが発生。このエラーはC++言語で構造体の「指示付集成体初期化」が正常に行われないことが原因で、C++のバージョンが2.0以上であれば、この初期化が有効(なはず)。−>参考
"cStandard“: "gnu99",
"cppStandard: "gnu++11"
のままだった。そこで、上記でGnu++20を選び、さらに,「c_cpp_properties.json」の記述も以下に変更、"cppStandard: "gnu++20"としてみたが、やはりエラー。(−>今後の宿題)
仕方ないので、「指示付集成体初期化」を諦め、「C言語方式」で初期化を行うと、今度はエラー無くコンパイルが終わり、スピーカーの動作の確認ができました。
| ▼AtomcS3R-Speaker_Basic.cpp(zip) | |
|---|---|
|
【SDカード上のWAVファイルの演奏】
上記参考ページの「Based on M5Unified Speaker API」をベースに、前記と同様にspk_cnfを初期化し、さらに幾つか修正や追加を行った。
SD設定で CS = -1 にしたため、GPIOエラーが出るが、SDカードに保存したfanfare4.wav(275kb)の再生ができた。
なお、WAVファイルの再生は本体ボタンでON/OFFできる(スイッチ応答が悪いが・・)。
※ ファイルサイズが大きいとメモリ不足(最大320kb程度)となるので、ファイルを分割して処理するか・・[−>☆
]。
| ▼Atomc_playWav.cpp(zip) ▼fanfare4.wav |
|---|
// ------------------- Audio Configuration -------------------
static constexpr const size_t output_samplerate = 44100; // 44.1kHz
static bool isPlaying = false; // Flag to track audio play state
// ------------------- Global File/Buffer Variables -------------------
File wavFile; // File object for WAV audio file
uint8_t* wavBuffer = nullptr; // Buffer to store entire WAV file
size_t wavBufferLen = 0; // Total length of WAV data in buffer
void setup() {
M5.begin();
M5.Display.setFont(&fonts::FreeMonoBold9pt7b);
M5.Display.setTextDatum(middle_center);
Serial.begin(115200);
// ------------------- SD Card Initialization -------------------
SPI.begin(SD_SPI_SCK_PIN, SD_SPI_MISO_PIN, SD_SPI_MOSI_PIN, SD_SPI_CS_PIN);
M5.Display.drawCenterString("SD Init...", 64, 0);
Serial.println("SD Init...");
// Attempt SD card init (25MHz SPI speed); halt on failure
if (!SD.begin(SD_SPI_CS_PIN, SPI, 25000000)) {
M5.Display.clear();
M5.Display.drawCenterString("SD Error!", 64, 50);
Serial.println("SD Error!");
while (1); // Infinite loop = halt if SD card fails
} else {
M5.Display.clear();
M5.Display.drawCenterString("SD Ready", 64, 0);
Serial.println("SD Ready");
}
// -------------- Speaker Configuration (I2S) -------------------
m5::speaker_config_t spk_cfg;
spk_cfg.pin_data_out = SPK_I2S_PIN_DATA;
spk_cfg.pin_bck = SPK_I2S_PIN_BCLK;
spk_cfg.pin_ws = SPK_I2S_PIN_LRCK;
spk_cfg.sample_rate = output_samplerate;
spk_cfg.dma_buf_len = 256; // DMA buffer size
spk_cfg.dma_buf_count = 6; // Number of DMA buffers
spk_cfg.i2s_port = i2s_port_t::I2S_NUM_0; // Use I2S hardware port 0
M5.Speaker.config(spk_cfg); // Apply speaker settings
// Initialize speaker; halt on failure
if(!M5.Speaker.begin()){
M5.Display.drawCenterString("SPK Error!", 64, 50);
Serial.println("SPK Error!");
while (1);
} else {
M5.Display.drawCenterString("SPK Ready", 64, 15);
Serial.println("SPK Ready\n");
}
M5.Speaker.setVolume(96);
delay(1000);
// ---------------- Display Initial Instructions -------------------
M5.Display.clear();
M5.Display.setTextColor(TFT_YELLOW);
M5.Display.drawCenterString("Press Screen", 64, 0);
M5.Display.drawCenterString("to Play/Stop", 64, 15);
M5.Display.setTextColor(TFT_WHITE);
// ------------- Load WAV File from SD Card -------------------
wavFile = SD.open(TEST_WAV_FILE, FILE_READ); //Open WAV file
// Halt if WAV file not found
if (!wavFile) {
M5.Display.drawCenterString("Find wav Error!", 64, 40);
Serial.println("Find wav Error!");
while (1);
} else {
M5.Display.drawCenterString("Find wav", 64, 40);
Serial.println("Find wav");
}
// Check freeHeap size
size_t freeHeap = ESP.getFreeHeap();
Serial.printf("Heap: %d byte\n",freeHeap);
// Allocate buffer to store entire WAV file
wavBufferLen = wavFile.size(); // Get total file size
wavBuffer = (uint8_t*)malloc(wavBufferLen); // Allocate memory
// Halt if memory allocation fails
if (wavBuffer == nullptr) {
Serial.println("Memory Error!");
wavFile.close();
while (1);
} else {
wavFile.read(wavBuffer, wavBufferLen); //Read entire file into buffer
wavFile.close(); // Close file
// Display WAV file size (convert bytes to KB)
String str_buf = String("Size:") + wavBufferLen/1024 + "KB";
M5.Display.drawCenterString(str_buf, 64, 55);
Serial.printf("Size: %d KB\n", wavBufferLen/1024);
}
M5.Display.drawCenterString("Stopped", 64, 80); // (stopped)
}
void loop() {
M5.update(); // detect button presses
if (M5.BtnA.wasClicked()) {
isPlaying = !isPlaying; // Flip play state
M5.Display.fillRect(0, 80, 128, 48, TFT_BLACK);
}
if (isPlaying) {
M5.Display.drawCenterString("Playing", 64, 80);
M5.Speaker.playWav(wavBuffer, wavBufferLen, 1, 0, false);
delay(2000);
} else {
M5.Display.drawCenterString("Stopped", 64, 80);
M5.Speaker.stop();
}
}
|
【おまけ】
オーディオファイルには多くの種類があり、特にWAV(Waveform Audio File Format)ファイルは、音をそのままデジタル化した無圧縮の音声ファイル形式で、その特徴は、
コロナ下から、しばらくJRに乗ることも無くなっていた(最近の移動は主にキャンカー)ので、スマホの機種変更後にモバイルSuicaの引越を行っていなかったが、急に東京に行くことになり、新スマホでモバイルSuicaの設定を行った。
最初、「新規登録」で(旧スマホと同じメールアドレスで)手続きを実施したところ、手続き最終画面で「エラー」となって、登録手続きができなかった(メールアドレス重複エラー?)。
そこで、「端末の変更」メニューで、以下のように、再度手続きを実施した。
参考:モバイルSuica(JR東日本)
で、新スマホでSuicaが使えるようになりました(旧スマホの残金も新スマホに移行できました)。
それにしても、旧スマホを、稼働可能状態で、残しておいて良かったです。
☆ ところで、Suicaのペンギンがなくなるのは、チョット寂しいですね。
【SD上のサイズが大きいWAVファイルをAtomicスピーカーベースで再生】
「Arduino入門」ページを参考に、SD上にあるサイズが大きいWAVファイルの再生を試みた。
| ▼AtomcS3R-Play.cpp(zip) ▼fanfare.wav ▼twinkle_twinkle.wav |
|---|
|
※プログラムのリストをハイライト無しのスタイルで見る場合はここをクリック
※ 本レポートの参考・利用は、あくまでも自己責任でお願いします。
![]() |
![]() |