// Local-sen-32
// 2023.3.2
// Arduino MEGA 2560 を使用する。
// PWM周波数を31kHzにする。

#define  AUT   55
#define  SRT   65
#define  VOL   A2
#define  GEN   A3
#define  CH1   58
#define  CH2   59
#define  CH3   60
#define  CH4   61
#define  TS1   22
#define  TS4   24
#define  TS2   26
#define  TS5   30
#define  TS6   32
#define  TS8   34
#define  TS3   38
#define  TS9   40
#define  TS7   42
#define  PIN4  46
#define  PIN1  48
#define  PIN2  50
#define  PIN3  52
#define  F1W   49
#define  F2W   51
#define  F3W   53
#define  F1C   41
#define  F2C   43
#define  F3C   45

#define  POUT1 23
#define  POUT2 25
#define  POUT3 27
#define  POUT4 29
#define  F11   12
#define  F12   11
#define  F21   10
#define  F22    9
#define  F31    5
#define  F32    4
#define  F12PWM 8
#define  F3PWM  7

  int vol;
  int gen;
  int duty;
  int i;
  int dnumber;
  int ts1;
  int ts2;
  int ts3;
  int ts4;
  int ts5;
  int ts6;
  int ts7;
  int ts8;
  int ts9;
  int strt;

void setup() {
  pinMode(VOL,INPUT);
  pinMode(GEN,INPUT);  
  pinMode(AUT,INPUT);
  pinMode(SRT,INPUT);
  pinMode(CH1,INPUT);
  pinMode(CH2,INPUT);
  pinMode(CH3,INPUT);
  pinMode(CH4,INPUT);
  pinMode(TS1,INPUT);
  pinMode(TS2,INPUT);
  pinMode(TS3,INPUT);
  pinMode(TS4,INPUT);
  pinMode(TS5,INPUT);
  pinMode(TS6,INPUT);
  pinMode(TS7,INPUT);
  pinMode(TS8,INPUT);
  pinMode(TS9,INPUT);
  pinMode(PIN4,INPUT);
  pinMode(PIN1,INPUT);
  pinMode(PIN2,INPUT);
  pinMode(PIN3,INPUT);
  pinMode(F1W,INPUT);
  pinMode(F2W,INPUT);
  pinMode(F3W,INPUT);
  pinMode(F1C,INPUT);
  pinMode(F2C,INPUT);
  pinMode(F3C,INPUT);
  
  pinMode(F11,OUTPUT);
  pinMode(F12,OUTPUT);
  pinMode(F21,OUTPUT);
  pinMode(F22,OUTPUT);
  pinMode(F31,OUTPUT);
  pinMode(F32,OUTPUT);
  pinMode(F12PWM,OUTPUT);
  pinMode(F3PWM,OUTPUT);
  pinMode(POUT1,OUTPUT);
  pinMode(POUT2,OUTPUT);
  pinMode(POUT3,OUTPUT);
  pinMode(POUT4,OUTPUT);

  TCCR4B = (TCCR4B & 0b11111000) | 0x01;   //Timer4を31KHzにする

  digitalWrite(F11,LOW);
  digitalWrite(F12,LOW);
  digitalWrite(F21,LOW);
  digitalWrite(F22,LOW);
  digitalWrite(F31,LOW);
  digitalWrite(F32,LOW);  
  analogWrite(F12PWM,0);
  analogWrite(F3PWM,0);  
  digitalWrite(POUT1,LOW);
  digitalWrite(POUT2,LOW);
  digitalWrite(POUT3,LOW);
  digitalWrite(POUT4,LOW);

  duty = 0;
}

void mode1(){
    digitalWrite(POUT1,LOW); delay(100);
    digitalWrite(POUT2,HIGH); delay(100);
    digitalWrite(POUT3,LOW); delay(100);
    digitalWrite(POUT4,LOW); delay(100);
    digitalWrite(F11,HIGH);
    digitalWrite(F12,LOW);
    digitalWrite(F21,HIGH);
    digitalWrite(F22,LOW);
    digitalWrite(F31,HIGH);
    digitalWrite(F32,LOW);
    
    for (i=0;i<20;i++){
      duty = analogRead(VOL)/4*i/20;
      analogWrite(F12PWM,duty);
      analogWrite(F3PWM,duty);
      delay(200);  
    }
    ts2 = digitalRead(TS2);
    while(ts2==LOW){
      duty = analogRead(VOL)/4;
      analogWrite(F12PWM,duty);
      analogWrite(F3PWM,duty);
      ts2 = digitalRead(TS2);
      delay(50);
    }
    vol = analogRead(VOL)/4;
    gen = analogRead(GEN)/4;
    for (i=0;i<20;i++){    
      duty =vol - (vol-gen)*i/20;
      analogWrite(F12PWM,duty);
      analogWrite(F3PWM,duty);
      delay(50);  
    }
    ts1 = digitalRead(TS1);
    while(ts1==LOW){
      duty = analogRead(GEN)/4;
      analogWrite(F12PWM,duty);
      analogWrite(F3PWM,duty);
      ts1 = digitalRead(TS1);
      delay(50);
    }
    digitalWrite(F11,LOW);
    digitalWrite(F21,LOW);
    digitalWrite(F31,LOW);
    delay(2000);
    return;
}

void mode2(){
    digitalWrite(POUT1,LOW); delay(100);
    digitalWrite(POUT2,HIGH); delay(100);
    digitalWrite(POUT3,HIGH); delay(100);
    digitalWrite(POUT4,LOW); delay(100);
    digitalWrite(F11,HIGH);
    digitalWrite(F12,LOW);
    digitalWrite(F21,HIGH);
    digitalWrite(F22,LOW);
    digitalWrite(F31,LOW);
    digitalWrite(F32,HIGH);

    for (i=0;i<20;i++){
      duty = analogRead(VOL)/4*i/20;
      analogWrite(F12PWM,duty);
      analogWrite(F3PWM,duty);
      delay(200);  
    }
    ts2 = digitalRead(TS2);
    while(ts2==LOW){
      duty = analogRead(VOL)/4;
      analogWrite(F12PWM,duty);
      analogWrite(F3PWM,duty);
      ts2 = digitalRead(TS2);
      delay(50);
    }
    vol = analogRead(VOL)/4;
    gen = analogRead(GEN)/4;
    for (i=0;i<20;i++){    
      duty =vol - (vol-gen)*i/20;
      analogWrite(F12PWM,duty);
      analogWrite(F3PWM,duty);
      delay(50);  
    }
    ts1 = digitalRead(TS1);
    while(ts1==LOW){
      duty = analogRead(GEN)/4;
      analogWrite(F12PWM,duty);
      analogWrite(F3PWM,duty);
      ts1 = digitalRead(TS1);
      delay(50);
    }
    digitalWrite(F11,LOW);
    digitalWrite(F21,LOW);
    digitalWrite(F32,LOW);
    delay(2000);
    return;
}

void mode3(){
    digitalWrite(POUT1,LOW); delay(100);
    digitalWrite(POUT2,HIGH); delay(100);
    digitalWrite(POUT3,LOW); delay(100);
    digitalWrite(POUT4,LOW); delay(100);
    digitalWrite(F11,LOW);
    digitalWrite(F12,HIGH);
    digitalWrite(F21,LOW);
    digitalWrite(F22,HIGH);
    digitalWrite(F31,LOW);
    digitalWrite(F32,HIGH);

    for (i=0;i<20;i++){
      duty = analogRead(VOL)/4*i/20;
      analogWrite(F12PWM,duty);
      analogWrite(F3PWM,duty);
      delay(200);  
    }
    ts1 = digitalRead(TS1);
    while(ts1==LOW){
      duty = analogRead(VOL)/4;
      analogWrite(F12PWM,duty);
      analogWrite(F3PWM,duty);
      ts1 = digitalRead(TS1);
      delay(50);
    }
    vol = analogRead(VOL)/4;
    gen = analogRead(GEN)/4;
    for (i=0;i<20;i++){    
      duty =vol - (vol-gen)*i/20;
      analogWrite(F12PWM,duty);
      analogWrite(F3PWM,duty);
      delay(50);  
    }
    ts2 = digitalRead(TS2);
    while(ts2==LOW){
      duty = analogRead(GEN)/4;
      analogWrite(F12PWM,duty);
      analogWrite(F3PWM,duty);
      ts2 = digitalRead(TS2);
      delay(50);
    }
    digitalWrite(F12,LOW);
    digitalWrite(F22,LOW);
    digitalWrite(F32,LOW);
    delay(2000);
    return;
}

void mode4(){
    digitalWrite(POUT1,LOW); delay(100);
    digitalWrite(POUT2,HIGH); delay(100);
    digitalWrite(POUT3,HIGH); delay(100);
    digitalWrite(POUT4,LOW); delay(100);
    digitalWrite(F11,LOW);
    digitalWrite(F12,HIGH);
    digitalWrite(F21,LOW);
    digitalWrite(F22,HIGH);
    digitalWrite(F31,HIGH);
    digitalWrite(F32,LOW);

    for (i=0;i<20;i++){
      duty = analogRead(VOL)/4*i/20;
      analogWrite(F12PWM,duty);
      analogWrite(F3PWM,duty);
      delay(200);  
    }
    ts1 = digitalRead(TS1);
    while(ts1==LOW){
      duty = analogRead(VOL)/4;
      analogWrite(F12PWM,duty);
      analogWrite(F3PWM,duty);
      ts1 = digitalRead(TS1);
      delay(50);
    }
    vol = analogRead(VOL)/4;
    gen = analogRead(GEN)/4;
    for (i=0;i<20;i++){    
      duty =vol - (vol-gen)*i/20;
      analogWrite(F12PWM,duty);
      analogWrite(F3PWM,duty);
      delay(50);  
    }
    ts2 = digitalRead(TS2);
    while(ts2==LOW){
      duty = analogRead(GEN)/4;
      analogWrite(F12PWM,duty);
      analogWrite(F3PWM,duty);
      ts2 = digitalRead(TS2);
      delay(50);
    }
    digitalWrite(F12,LOW);
    digitalWrite(F22,LOW);
    digitalWrite(F31,LOW);
    delay(2000);
    return;
}

void loop(){
  if (digitalRead(AUT)==LOW){     //手動運転モード
      vol = analogRead(VOL);
      if (digitalRead(PIN1)==HIGH){                //ポイント1 操作
        digitalWrite(POUT1,HIGH);
        delay(100);
      } else {
        digitalWrite(POUT1,LOW);
        delay(100);
      }
      if (digitalRead(PIN2)==HIGH){                //ポイント2 操作
        digitalWrite(POUT2,HIGH);
        delay(100);
      } else {
        digitalWrite(POUT2,LOW);
        delay(100);
      }
      if (digitalRead(PIN3)==HIGH){                //ポイント3 操作
        digitalWrite(POUT3,HIGH);
        delay(100);
      } else {
        digitalWrite(POUT3,LOW);
        delay(100);
      }
      if (digitalRead(PIN4)==HIGH){                //ポイント4 操作
        digitalWrite(POUT4,HIGH);
        delay(100);
      } else {
        digitalWrite(POUT4,LOW);
        delay(100);
      }

      if (digitalRead(F1W)==HIGH){           //F1 進行方向設定
        digitalWrite(F11,HIGH);
      }  else {
        digitalWrite(F11,LOW);
      }
      if (digitalRead(F1C)==HIGH){
        digitalWrite(F12,HIGH);
      } else {
        digitalWrite(F12,LOW);
      }
      if (digitalRead(F2W)==HIGH){           //F2 進行方向設定
        digitalWrite(F21,HIGH);
      }  else {
        digitalWrite(F21,LOW);
      }
      if (digitalRead(F2C)==HIGH){
        digitalWrite(F22,HIGH);
      } else {
        digitalWrite(F22,LOW);
      }
      if (digitalRead(F3W)==HIGH){           //F3 進行方向設定
        digitalWrite(F31,HIGH);
      }  else {
        digitalWrite(F31,LOW);
      }
      if (digitalRead(F3C)==HIGH){
        digitalWrite(F32,HIGH);
      } else {
        digitalWrite(F32,LOW);
      }
      
      duty=vol/4;
      analogWrite(F12PWM,duty);
      analogWrite(F3PWM,duty);
      
  } else if (digitalRead(AUT)==HIGH && digitalRead(SRT)==HIGH){   //自動運転モード
      analogWrite(F12PWM, 0);  //暴走防止
      analogWrite(F3PWM, 0); 
      
      dnumber = 1;            //ダイヤルの数字をデコード
      if (digitalRead(CH1)==LOW){dnumber=dnumber+1;}
      if (digitalRead(CH2)==LOW){dnumber=dnumber+2;}
      if (digitalRead(CH3)==LOW){dnumber=dnumber+4;}
      if (digitalRead(CH4)==LOW){dnumber=dnumber+8;}
      
      switch(dnumber){        //モード選択
        case 1: mode1(); break;
        case 2: mode2(); break;
        case 3: mode3(); break;
        case 4: mode4(); break;
      }
  }
  delay(10);
}