概要
- 前回、Grove接続(シリアル)で受け取ってLCDに表示できるようにしたが、受信側のM5Stackの処理について単純に(1)データ受け取る→(2)LCD表示→(1)データ受け取る→・・・と順番に繰り返していたので、(1)と(2)で待ち時間が両方独立して必要だった。
- 今回は、バッファを持たせることで(1)と(2)の待ち時間を重複させてちょっとだけ早くする。
コード
送信側:Timer Camera / Unit Cam
前回と同じ
#include "esp_camera.h"
void setup() {
Serial.begin(115200);
Serial1.begin(115200, SERIAL_8N1, 13, 4);
camera_config_t config;
config.ledc_channel = LEDC_CHANNEL_0;
config.ledc_timer = LEDC_TIMER_0;
config.pin_d0 = 32;
config.pin_d1 = 35;
config.pin_d2 = 34;
config.pin_d3 = 5;
config.pin_d4 = 39;
config.pin_d5 = 18;
config.pin_d6 = 36;
config.pin_d7 = 19;
config.pin_xclk = 27;
config.pin_pclk = 21;
config.pin_vsync = 22;
config.pin_href = 26;
config.pin_sccb_sda = 25;
config.pin_sccb_scl = 23;
config.pin_pwdn = -1;
config.pin_reset = 15;
config.xclk_freq_hz = 20000000;
config.pixel_format = PIXFORMAT_JPEG;
config.frame_size = FRAMESIZE_QVGA;
config.jpeg_quality = 30;
config.fb_count = 2;
config.grab_mode = CAMERA_GRAB_LATEST;
config.fb_location = CAMERA_FB_IN_PSRAM;
esp_err_t err = esp_camera_init(&config);
if (err != ESP_OK) {
Serial.printf("Camera init failed with error 0x%x", err);
return;
}
sensor_t *s = esp_camera_sensor_get();
s->set_vflip(s, 1);
}
void loop() {
camera_fb_t *fb = esp_camera_fb_get();
if (fb) {
Serial1.print("DATA");
Serial1.write((byte *)&(fb->len), 4);
Serial1.write(fb->buf, fb->len);
esp_camera_fb_return(fb);
}
}
受信側:M5Stack
バッファを2つ用意して、空いてる方に入れる&入ってる方を表示するだけ。
#include <M5Stack.h>
uint8_t buf[4];
uint8_t buf1[10000];
volatile size_t data_size1 = 0;
uint8_t buf2[10000];
volatile size_t data_size2 = 0;
void setup() {
M5.begin();
Serial.begin(115200);
Serial1.begin(115200, SERIAL_8N1, 21, 22);
xTaskCreatePinnedToCore(subProcess, "subProcess", 4096, NULL, 1, NULL, 1);
}
void loop() {
if (Serial1.available() > 4){
if (Serial1.read() == 'D') {
if (Serial1.read() == 'A') {
if (Serial1.read() == 'T') {
if (Serial1.read() == 'A') {
Serial1.readBytes(buf, 4);
size_t temp = buf[0] | buf[1] << 8 | buf[2] << 16 | buf[3] << 24 ;
while (1) {
if (data_size1 == 0) {
Serial1.readBytes(buf1, temp);
data_size1 = temp;
break;
}
else if (data_size2 == 0) {
Serial1.readBytes(buf2, temp);
data_size2 = temp;
break;
}
}
}
}
}
}
}
}
void subProcess(void * pvParameters) {
while (1) {
if (data_size1 != 0) {
M5.Lcd.drawJpg(buf1, data_size1, 0, 0, 320, 240);
data_size1 = 0;
}
else if (data_size2 != 0) {
M5.Lcd.drawJpg(buf2, data_size2, 0, 0, 320, 240);
data_size2 = 0;
}
}
}
結果