Raspberry Pi Pico で鉄道模型を動かす

(1) pico側に書き込んだスケッチ

#include <hardware/pwm.h>

void pico_analogWriteFreqRang(int pin, float freq, uint32_t rang)
// rang=[0,65535], freq > 125000000.0 / (rang + 1) / 256
// slice0: GP0,  GP1,  GP16, GP17
// slice1: GP2,  GP3,  GP18, GP19
// slice2: GP4,  GP5,  GP20, GP21
// slice3: GP6,  GP7,  GP22
// slice4: GP8,  GP9,  GP25
// slice5: GP10, GP11, GP26, GP27
// slice6: GP12, GP13, GP28
// slice7: GP14, GP15
// [註]sliceが同じものは、freqとrangは共通になる.
{
    int slice_num = pwm_gpio_to_slice_num(pin);
    float tmp = (rang + 1) * freq;
    gpio_set_function(pin, GPIO_FUNC_PWM);
    pwm_set_clkdiv(slice_num, 125000000.0 / tmp); // 256未満.
    pwm_set_wrap(slice_num, rang);
}

void pico_analogWrite(int pin, uint32_t val)
{
    int slice_num = pwm_gpio_to_slice_num(pin);
    int ch = PWM_CHAN_A;
    if ((pin & 1) != 0) { ch = PWM_CHAN_B; }
    pwm_set_chan_level(slice_num, ch, val);
    pwm_set_enabled(slice_num, true);
}

void setup() { Serial.begin(115200); }

int prm_f0[4][4], prm_f1[8][4], prm_f2[3] = { A0, A1, A2 };

void loop()
{
    int c = Serial.read(), ch = 0, p0, p1, p2;
    if (c < 0) { delay(3); }
    if (0xf0 <= c && c <= 0xf7) {
      while (Serial.available() < 1) {}
      ch = Serial.read();
    }
    if (c == 0xf0) { 
        while (Serial.available() < 3) {}
        p0 = Serial.read();
        p1 = Serial.read();
        p2 = Serial.read();
        if (0 <= ch && ch <= 3) {
            prm_f0[ch][0] = p0;
            prm_f0[ch][1] = p1;
            prm_f0[ch][2] = p2;
            pinMode(p0, OUTPUT);
            pinMode(p1, OUTPUT);
            pinMode(p2, OUTPUT);
            pico_analogWriteFreqRang(p0, 100 * 1000, 255); // 100KHz
            pico_analogWrite(p0, 0);
            digitalWrite(p1, LOW);
            digitalWrite(p2, LOW);
        }
    }
    if (c == 0xf1) { 
        while (Serial.available() < 3) {}
        p0 = Serial.read();
        p1 = Serial.read();
        p2 = Serial.read();
        if (0 <= ch && ch <= 7) {
            prm_f1[ch][0] = p0;
            prm_f1[ch][1] = p1;
            prm_f1[ch][2] = p2;
            pinMode(p1, OUTPUT);
            pinMode(p2, OUTPUT);
            digitalWrite(p1, LOW);
            digitalWrite(p2, LOW);
        }
    }
    if (c == 0xf2) {
        if (0 <= ch && ch <= 2) {
        //  pinMode(prm_f2[ch], INPUT);
        }
    }
    if (c == 0xf4) {
        p0 = (ch >> 6) & 3;
        ch &= 63;
        if (0 <= ch && ch <= 3) {
            p1 = prm_f0[ch][1];
            p2 = prm_f0[ch][2];
            if (p0 == 0) { digitalWrite(p1, LOW);  digitalWrite(p2, LOW);  }
            if (p0 == 1) { digitalWrite(p1, HIGH); digitalWrite(p2, LOW);  }
            if (p0 == 2) { digitalWrite(p1, LOW);  digitalWrite(p2, HIGH); }
            if (p0 == 3) { digitalWrite(p1, HIGH); digitalWrite(p2, HIGH); }
        }
    }
    if (c == 0xf5) {
        while (Serial.available() < 1) {}
        p1 = Serial.read();
        if (0 <= ch && ch <= 3) {
            p0 = prm_f0[ch][0];
            pico_analogWrite(p0, p1);
        }
    }
    if (c == 0xf6) {
        p0 = (ch >> 6) & 3;
        ch &= 63;
        if (0 <= ch && ch <= 7) {
            p1 = prm_f1[ch][1];
            p2 = prm_f1[ch][2];
            if (p0 == 0) { digitalWrite(p1, LOW);  digitalWrite(p2, LOW);  }
            if (p0 == 1) { digitalWrite(p1, HIGH); digitalWrite(p2, LOW);  }
            if (p0 == 2) { digitalWrite(p1, LOW);  digitalWrite(p2, HIGH); }
            if (p0 == 3) { digitalWrite(p1, HIGH); digitalWrite(p2, HIGH); }
            p0 = prm_f1[ch][0];
            digitalWrite(25, 1); // for-debug
            delay(p0 * 8); // max2sec.
            digitalWrite(25, 0); // for-debug
            digitalWrite(p1, LOW);  digitalWrite(p2, LOW);
        }
    }
    if (c == 0xf7) {
        if (0 <= ch && ch <= 2) {
            p0 = prm_f2[ch];
            p1 = analogRead(p0);
            Serial.write((p1 >> 8) & 255);
            Serial.write( p1       & 255);
        }
    }
}

トップ   新規 一覧 単語検索 最終更新   ヘルプ   最終更新のRSS