LoginSignup
0
0

More than 5 years have passed since last update.

Funtion Decoder

Posted at

Overview

Smile Function Decoder for NMRA Lib.

Comment

dec/8/2018
Fix notifyDccReset processing.

1)Added initialization of gState_Fn variable.
//------------------------------------------------------------------
// Reset
//------------------------------------------------------------------
void notifyDccReset(uint8_t hardReset )
{
digitalWrite(O1,LOW);
digitalWrite(O2,LOW);
digitalWrite(O3,LOW);
digitalWrite(O4,LOW);

 gState_F0 = 0; // ADD
 gState_F1 = 0; // ADD
 gState_F2 = 0; // ADD
 gState_F3 = 0; // ADD
 gState_F4 = 0; // ADD
 gState_F5 = 0; // ADD
}

2)DCC reset pulse emulation added.
if (Speed > 64) {
doing_Resets_Flag = true;
notifyDccReset(0);
} else {
doing_Resets_Flag = false;
}

link

https://twitter.com/masashi_214
http://ayabu.blog.shinobi.jp/
http://dcc.client.jp/
http://www007.upp.so-net.ne.jp/nagoden/

// 20181208 Kenneth west TEST Program ADD
//
// DCC Function Decoder Rev 2 for DS-DCC decode
// By yaasan
// Based on Nicolas's sketch http://blog.nicolas.cx
// Inspired by Geoff Bunza and his 17 Function DCC Decoder & updated library
// http://dcc.client.jp
// http://ayabu.blog.shinobi.jp
// O1:F3 でON/OFF head sign
// O2:F0 でON/OFF head light
// O3:F1 でON/OFF tail light
// O4:F5 でON/OFF room light

#include "NmraDcc.h"
#include <avr/eeprom.h>  //required by notifyCVRead() function if enabled below

bool doing_Resets_Flag = false;  // True if we are simulating reset packets.

//FX効果
//Cmd,Time,Val,Frq
//I:初期状態,O:出力,S:スイープ,L:ループ,E:終了
unsigned char ptn1[2][3]={{'I',0,255},{'E',0,255}}; //10ms すぐ点灯
unsigned char ptn2[3][3]={{'I',0,5},{'S',100,255},{'E',0,255}}; //10ms もやっと点灯
unsigned char ptn3[4][3]={{'I',0,5},{'S',50,255},{'S',50,5},{'L',0,5}}; //10ms 三角波
unsigned char ptn4[6][3]={{'I',0,0},{'O',10,255},{'O',10,125},{'O',10,255},{'O',10,80},{'L',0,0}}; // ランダム
unsigned char ptn5[6][3]={{'I',0,0},{'S',50,255},{'S',50,0},{'S',50,128},{'S',50,0},{'L',0,0}};//マーズライト
unsigned char ptn6[4][3]={{'I',0,0},{'O',30,255},{'S',20,128},{'L',0,0}};//フラッシュライト
unsigned char ptn7[4][3]={{'I',0,0},{'O',20,255},{'O',80,0},{'L',0,0}}; //シングルパルスストロボ
unsigned char ptn8[6][3]={{'I',0,0},{'O',10,255},{'O',20,0},{'O',10,255},{'O',60,0},{'L',0,0}}; //ダブルパルスストロボ
unsigned char ptn9[6][3]={{'I',0,0},{'O',25,128},{'O',40,255},{'O',25,128},{'O',40,0},{'L',0,0}}; //ミディアムパルスストロボ
unsigned char ptn10[8][3]={{'I',0,0},{'O',1,255},{'O',1,0},{'O',1,255},{'O',30,0},{'O',10,50},{'O',100,255},{'E',0,0}}; //グロー管蛍光灯
unsigned char ptn11[9][3]={{'I',0,0},{'O',1,255},{'O',1,0},{'O',1,255},{'O',30,0},{'O',30,40},{'O',50,255},{'O',70,0},{'L',0,0}}; //グロー管蛍光灯切れそう
unsigned char (*ptn)[3];

//各種設定、宣言

#define DECODER_ADDRESS 3
#define DCC_ACK_PIN 0   // Atiny85 PB0(5pin) if defined enables the ACK pin functionality. Comment out to disable.
//                      // Atiny85 DCCin(7pin)
#define O1 0            // Atiny85 PB0(5pin)             head sign light
#define O2 1            // Atiny85 PB1(6pin) analogwrite Head light
#define O3 3            // Atint85 PB3(2pin)             tail light
#define O4 4            // Atiny85 PB4(3pin) analogwrite room light

#define MAX_PWMDUTY 255
#define MID_PWMDUTY 10

#define CV_VSTART       2
#define CV_ACCRATIO     3
#define CV_DECCRATIO    4
#define CV_F0_FORWARD 33
#define CV_F0_BACK 34
#define CV_F1 35
#define CV_F2 36
#define CV_F3 37
#define CV_F4 38
#define CV_F5 39
#define CV_F6 40
#define CV_F7 41
#define CV_F8 42
#define CV_F9 43
#define CV_F10 44
#define CV_F11 45
#define CV_F12 46
#define CV_49_F0_FORWARD_LIGHT 49
#define CV_DIMMING_SPEED 50
#define CV_DIMMING_LIGHT_QUANTITY 51
#define CV_ROOM_DIMMING 52

//ファンクションの変数
uint8_t fn_bit_f0 = 0;
uint8_t fn_bit_f1 = 0;
uint8_t fn_bit_f2 = 0;
uint8_t fn_bit_f3 = 0;
uint8_t fn_bit_f4 = 0;
uint8_t fn_bit_f5 = 0;
uint8_t fn_bit_f6 = 0;
uint8_t fn_bit_f7 = 0;
uint8_t fn_bit_f8 = 0;
uint8_t fn_bit_f9 = 0;
uint8_t fn_bit_f10 = 0;
uint8_t fn_bit_f11 = 0;
uint8_t fn_bit_f12 = 0;
uint8_t fn_bit_f13 = 0;
uint8_t fn_bit_f14 = 0;
uint8_t fn_bit_f15 = 0;
uint8_t fn_bit_f16 = 0;
uint8_t fn_bit_f17 = 0;
uint8_t fn_bit_f18 = 0;
uint8_t fn_bit_f19 = 0;
uint8_t fn_bit_f20 = 0;
uint8_t fn_bit_f21 = 0;
uint8_t fn_bit_f22 = 0;
uint8_t fn_bit_f23 = 0;
uint8_t fn_bit_f24 = 0;
uint8_t fn_bit_f25 = 0;
uint8_t fn_bit_f26 = 0;
uint8_t fn_bit_f27 = 0;
uint8_t fn_bit_f28 = 0;

//使用クラスの宣言
NmraDcc  Dcc;
DCC_MSG  Packet;

//Task Schedule
unsigned long gPreviousL5 = 0;

//進行方向
uint8_t gDirection = 128;

//Function State
uint8_t gState_F0 = 0;
uint8_t gState_F1 = 0;
uint8_t gState_F2 = 0;
uint8_t gState_F3 = 0;
uint8_t gState_F4 = 0;
uint8_t gState_F5 = 0;
uint8_t gState_F6 = 0;
uint8_t gState_F7 = 0;
uint8_t gState_F8 = 0;
uint8_t gState_F9 = 0;
uint8_t gState_F10 = 0;
uint8_t gState_F11 = 0; 
uint8_t gState_F12 = 0;
//モータ制御関連の変数
uint32_t gSpeedRef = 1;

//CV related
uint8_t gCV1_SAddr = 3; 
uint8_t gCVx_LAddr = 3;
uint8_t gCV49_fx = 20;
uint8_t gCV50_DimmingSpeed = 1;
uint8_t gCV51_DimmingLightQuantity = 10;
uint8_t gCV52_RoomDimming = 128;

//Internal variables and other.
#if defined(DCC_ACK_PIN)
const int DccAckPin = DCC_ACK_PIN ;
#endif

struct CVPair {
  uint16_t  CV;
  uint8_t   Value;
};
CVPair FactoryDefaultCVs [] = {
  {CV_MULTIFUNCTION_PRIMARY_ADDRESS, DECODER_ADDRESS}, // CV01
  {CV_ACCESSORY_DECODER_ADDRESS_MSB, 0},               // CV09 The LSB is set CV 1 in the libraries .h file, which is the regular address location, so by setting the MSB to 0 we tell the library to use the same address as the primary address. 0 DECODER_ADDRESS
  {CV_MULTIFUNCTION_EXTENDED_ADDRESS_MSB, 0},          // CV17 XX in the XXYY address
  {CV_MULTIFUNCTION_EXTENDED_ADDRESS_LSB, 0},          // CV18 YY in the XXYY address
  {CV_29_CONFIG, 128 },                                // CV29 Make sure this is 0 or else it will be random based on what is in the eeprom which could caue headaches
  {CV_49_F0_FORWARD_LIGHT, 20},                        // CV49 F0 Forward Light
  {CV_DIMMING_SPEED, 1},
  {CV_DIMMING_LIGHT_QUANTITY,10},
  {CV_ROOM_DIMMING, 100},
};

void(* resetFunc) (void) = 0;  //declare reset function at address 0
void LightMes( char,char );
void pulse(void);
uint8_t FactoryDefaultCVIndex = sizeof(FactoryDefaultCVs) / sizeof(CVPair);

void notifyDccReset(uint8_t hardReset );

//uint16_t limitSpeed(uint16_t inSpeed);

void notifyCVResetFactoryDefault()
{
  //When anything is writen to CV8 reset to defaults.

  resetCVToDefault();
  //Serial.println("Resetting...");
  delay(1000);  //typical CV programming sends the same command multiple times - specially since we dont ACK. so ignore them by delaying

  resetFunc();
};

//------------------------------------------------------------------
// Reset
//------------------------------------------------------------------
void notifyDccReset(uint8_t hardReset )
{
  digitalWrite(O1,LOW);
  digitalWrite(O2,LOW);
  digitalWrite(O3,LOW);
  digitalWrite(O4,LOW);

  gState_F0 = 0; // ADD
  gState_F1 = 0; // ADD
  gState_F2 = 0; // ADD
  gState_F3 = 0; // ADD
  gState_F4 = 0; // ADD
  gState_F5 = 0; // ADD
}

//------------------------------------------------------------------
// CVをデフォルトにリセット
// Serial.println("CVs being reset to factory defaults");
//------------------------------------------------------------------
void resetCVToDefault()
{
  for (int j = 0; j < FactoryDefaultCVIndex; j++ ) {
    Dcc.setCV( FactoryDefaultCVs[j].CV, FactoryDefaultCVs[j].Value);
  }
};



extern void    notifyCVChange( uint16_t CV, uint8_t Value) {
  //CVが変更されたときのメッセージ
  //Serial.print("CV ");
  //Serial.print(CV);
  //Serial.print(" Changed to ");
  //Serial.println(Value, DEC);
};

//------------------------------------------------------------------
// CV Ack
//------------------------------------------------------------------
void notifyCVAck(void)
{
  //Serial.println("notifyCVAck");
  digitalWrite(O1,HIGH);
  digitalWrite(O2,HIGH);
  digitalWrite(O3,HIGH);
  digitalWrite(O4,HIGH);

  delay( 6 );

  digitalWrite(O1,LOW);
  digitalWrite(O2,LOW);
  digitalWrite(O3,LOW);
  digitalWrite(O4,LOW);
}

//------------------------------------------------------------------
// Arduino固有の関数 setup() :初期設定
//------------------------------------------------------------------
void setup()
{
  //シリアル通信開始
  //Serial.begin(115200);

  //D9,D10 PWM キャリア周期:31kHz
//  TCCR1 &= B11110000;
//  TCCR1 |= B00000001;

  //PWMを10bit化
  //TCCR1A |= B00000011;

//    TCCR0A = 2<<COM0A0 | 2<<COM0B0 | 3<<WGM00;
 //   TCCR0B = 0<<WGM02 | 1<<CS00;    
 //   TCCR1 = 0<<PWM1A | 0<<COM1A0 | 1<<CS10;
 //   GTCCR = 1<<PWM1B | 2<<COM1B0;
#if 0
  TCCR0A = 2<<COM0A0 | 2<<COM0B0 | 3<<WGM00; // B1111 0011
  TCCR0B = 0<<WGM02 | 1<<CS00;               // B0000 0001 分周無し
  TCCR1 = 0<<PWM1A | 0<<COM1A0 | 1<<CS10;
  GTCCR = 1<<PWM1B | 2<<COM1B0;  
#endif

// TCCR1 =0x03;最初に0x03が設定されている。
// D9,D10 PWM キャリア周期:31kHz
// TCCR1 &= B11110000;
// TCCR1 |= B00000001;

//TCCR1 = 1<<CTC1 | 1<<PWM1A | 3<<COM1A0 | 1<<CS10;
  TCCR1 = 0<<CTC1 | 0<<PWM1A | 0<<COM1A0 | 1<<CS10;

  pinMode(O1, OUTPUT);
  pinMode(O2, OUTPUT);
  pinMode(O3, OUTPUT);
  pinMode(O4, OUTPUT);

  //DCCの応答用負荷ピン
#if defined(DCCACKPIN)
  //Setup ACK Pin
  pinMode(DccAckPin, OUTPUT);
  digitalWrite(DccAckPin, 0);
#endif

#if !defined(DECODER_DONT_DEFAULT_CV_ON_POWERUP)
  if ( Dcc.getCV(CV_MULTIFUNCTION_PRIMARY_ADDRESS) == 0xFF ) {   //if eeprom has 0xFF then assume it needs to be programmed
    //Serial.println("CV Defaulting due to blank eeprom");
    notifyCVResetFactoryDefault();

  } else {
    //Serial.println("CV Not Defaulting");
  }
#else
  //Serial.println("CV Defaulting Always On Powerup");
  notifyCVResetFactoryDefault();
#endif

  // Setup which External Interrupt, the Pin it's associated with that we're using, disable pullup.
  Dcc.pin(0, 2, 0); // Atiny85 7pin(PB2)をDCC_PULSE端子に設定

  // Call the main DCC Init function to enable the DCC Receiver
  Dcc.init( MAN_ID_DIY, 100,   FLAGS_MY_ADDRESS_ONLY , 0 );

  //Reset task
  gPreviousL5 = millis();

  //Init CVs
  gCV1_SAddr = Dcc.getCV( CV_MULTIFUNCTION_PRIMARY_ADDRESS ) ;

//#if 0
  gCV49_fx = Dcc.getCV( CV_49_F0_FORWARD_LIGHT );
  switch(gCV49_fx){
    case 0: ptn = ptn1;
    break;
    case 1: ptn = ptn1;
    break;
    case 2: ptn = ptn2;
    break;
    case 3: ptn = ptn3;    
    break;
    case 4: ptn = ptn4;
    break;
    case 5: ptn = ptn5;
    break;
    case 6: ptn = ptn6;
    break;
    case 7: ptn = ptn7;
    break;
    case 8: ptn = ptn8;
    break;
    case 9: ptn = ptn9;
    break;
    case 10: ptn = ptn10;
    break;
    case 11: ptn = ptn11;
    break;
  }
  gCV50_DimmingSpeed  = Dcc.getCV( CV_DIMMING_SPEED );          // 減光スピード
  gCV51_DimmingLightQuantity = Dcc.getCV( CV_DIMMING_LIGHT_QUANTITY );  // 減光レベル
  gCV52_RoomDimming = Dcc.getCV( CV_ROOM_DIMMING );
//#endif

//デバック信号:起動  
//注意:2016/4/9 このコメントを外し起動時にアドレスを点灯させるようにすると、
//      loopにたどり着く時間が長くなり、CV書き込みが失敗します。
//LightMes(0);
//LightMes(Dcc.getCV(CV_MULTIFUNCTION_PRIMARY_ADDRESS));
//LightMes(gCV49_fx,8);

//O2 analog test 明るく点灯ぃて1秒後に暗くなる
//OCR1A有効   high出力          分周無し 
#if 0
TCCR1 = 1<<PWM1A | 2<<COM1A0 | 1<<CS10; 
OCR1A = 255;
delay(1000);
OCR1A = 12;
for(;;);
#endif
}

//---------------------------------------------------------------------
// Arduino main loop
//---------------------------------------------------------------------
void loop() {
  // You MUST call the NmraDcc.process() method frequently from the Arduino loop() function for correct library operation
  Dcc.process();

  if ( (millis() - gPreviousL5) >= 10) // 100:100msec  10:10msec  Function decoder は 10msecにしてみる。
  {
    //Headlight control
    HeadLight_Control();

    //Motor drive control
    //Motor_Control();

    //Reset task
    gPreviousL5 = millis();
  }
}


//---------------------------------------------------------------------
// HeadLight control Task (10Hz:100ms)
//---------------------------------------------------------------------
void HeadLight_Control()
{
  uint16_t aPwmRef = 0;

  if((gCV49_fx >= 2) && (gCV49_fx <= 11)) {
    FXeffect_Control();
  }

//---------------------------------------------------------------------
// ヘッド・テールライトコントロール
// CV49=20 設定で有効
// F0 で On/Off O2:head O3:tail 
//--------------------------------------------------------------------- 
  if(gCV49_fx == 20) {
    if(gState_F0 > 0) {
      if( gDirection == 0){                // Reverse 後進(DCS50Kで確認)

        TCCR1 = 1<<CS10;            // OCR1A 無効
        OCR1A = 0;                  // O2:analog out (hedd light) 
        digitalWrite(O3, HIGH);            // 点灯

      } else {                             // Forward 前進(DCS50Kで確認)
        digitalWrite(O3, LOW);             // O3:tail light off
        //               OCR1A有効   high出力          分周無し 
        TCCR1 = 1<<PWM1A | 2<<COM1A0 | 1<<CS10; 

        if ( gSpeedRef > 1 ){//gCV50_DimmingSpeed ){    // 調光機能
          aPwmRef = MAX_PWMDUTY;          // 速度が1以上だったらMAX
        } else {
          aPwmRef = 10;//gCV51_DimmingLightQuantity;    // 減光レベル
        }

        OCR1A = aPwmRef;                  // O2:analog out (hedd light)
      }
    }

    if(gState_F0 == 0){                   // DCC F0 コマンドの処理
      TCCR1 = 1<<CS10; 
      OCR1A = 0;                          // O2:analog out (hedd light) 
      digitalWrite(O2, LOW);              // 消灯
      digitalWrite(O3, LOW);              // 消灯
    }
  }


//---------------------------------------------------------------------
// ヘッド・テールライトコントロール
// CV49=21 設定で有効
// F0 で On/Off O2:head O3:tail 
//--------------------------------------------------------------------- 
  if(gCV49_fx == 21) {
    if(gState_F0 > 0) {
      if( gDirection == 1){                // Reverse 前進(DCS50Kで確認)
        digitalWrite(O2, HIGH);
        digitalWrite(O3, LOW);
      } else {                             // Forward 後進(DCS50Kで確認)
        digitalWrite(O2, LOW);
        digitalWrite(O3, HIGH);
      }
    }
    if(gState_F0 == 0) {
        digitalWrite(O2, LOW);  
        digitalWrite(O3, LOW);
    }
  }

//---------------------------------------------------------------------
// ヘッド・テールライトコントロール
// CV49=0,1 設定で有効
// F0 で Head Light On/Off F1 Tail Light On/Off F3 HEAD sign F5 room 
//--------------------------------------------------------------------- 

// F0 受信時の処理
//#if 
  if((gCV49_fx != 20)||(gCV49_fx != 20)) {
    if(gState_F0 == 0){
      digitalWrite(O2, LOW);
    } else {
      digitalWrite(O2, HIGH);
    }
//#endif

// F1 受信時の処理
//#if 
    if(gState_F1 == 0){
      digitalWrite(O3, LOW);
    } else {
      digitalWrite(O3, HIGH);
    }
//#endif  
  }

//---------------------------------------------------------------------
// ヘッド・テールライトコントロール
// F3 と F5の処理
//--------------------------------------------------------------------- 

// F2 受信時の処理
// DCS50KのF2は1shotしか光らないので、コメントアウト
#if 0 
  if(gCV49_fx < 20 ) {  // CV49 が20 または21 以外有効
    if(gState_F2 == 0){                   
      digitalWrite(O2, LOW);  
    } else {
      digitalWrite(O2, HIGH);
    }
  }
#endif

// F3 受信時の処理
//#if 0
  if(gState_F3 == 0){
    digitalWrite(O1, LOW);
  } else {
    digitalWrite(O1, HIGH);
  }
//#endif

// F4 受信時の処理
#if 0
  if(gState_F4 == 0){
    digitalWrite(O4, LOW);
  } else {
    digitalWrite(O4, HIGH);
  }
#endif

// F5 受信時の処理
  if(gState_F5 == 0){
    GTCCR = 0 << PWM1B | 0 << COM1B0;
    analogWrite(O4, 0);
    digitalWrite(O4, LOW);               // 消灯
  } else {
    GTCCR = 1 << PWM1B | 2 << COM1B0;
    analogWrite(O4,gCV52_RoomDimming);
  }
}



//DCC速度信号の受信によるイベント
//extern void notifyDccSpeed( uint16_t Addr, uint8_t Speed, uint8_t ForwardDir, uint8_t MaxSpeed )
extern void notifyDccSpeed( uint16_t Addr, DCC_ADDR_TYPE AddrType, uint8_t Speed, DCC_DIRECTION Dir, DCC_SPEED_STEPS SpeedSteps )
{
  if (Speed > 64) {
//  if(doing_Resets_Flag == false) {
      doing_Resets_Flag = true;
      notifyDccReset(0);
//    }
  }
    else {
          doing_Resets_Flag = false;
    }



//  if ( gDirection != ForwardDir) // old NMRA
  if ( gDirection != Dir )
  {
//  gDirection = ForwardDir; // old NMRA
    gDirection = Dir;
  }
  gSpeedRef = Speed;
}




//---------------------------------------------------------------------
// FX効果ステートマシン
// 10ms周期で起動
// unsigned chart ptn[4][5]{{'I',0,0,1},{'S',20,255,1},{'S',40,0,1},{'E',0,0,1}};
//---------------------------------------------------------------------
void FXeffect_Control(){
  static char state = 0;    // ステート
  static unsigned char adr = 0;      // アドレス
  static int timeUp = 0;    // 時間
  static float delt_v = 0;  // 100msあたりの増加量 
  static float pwmRef =0;

  if(gState_F0 == 0){ // F0 OFF
    state = 0; 
    adr = 0;
    timeUp = 0;
    pwmRef = 0;
    // OCR1A無効   OCR1A未使用  分周無し O2:消灯させる 
    TCCR1 = 1<<CS10; 
    digitalWrite(O2, LOW); // PB1:O2:6pin LOW出力
  }

  S00:  
  switch(state){
    case 0: // S00:idel
      if(gState_F0 >0){ // F0 ON
        adr = 0;
        timeUp = 0;
        pwmRef = 0;
        //               OCR1A有効   high出力          分周無し 
        TCCR1 = 1<<PWM1A | 2<<COM1A0 | 1<<CS10; 
        OCR1A = 0;
        state = 1;
        goto S00;     // 100ms待たずに再度ステートマシーンに掛ける
      }
      break;

    case 1: // S01:コマンド処理
        if( ptn[adr][0]=='I'){ // I:初期化
          timeUp = ptn[adr][1];
          pwmRef = ptn[adr][2];
          delt_v = 0; // 変化量0
          OCR1A = (unsigned char)pwmRef;                  // O2:analog out (hedd light)
          adr++;
          state = 1;
          goto S00;   // 100ms待たずに再度ステートマシーンに掛ける
        } else if( ptn[adr][0]=='E'){ // E:end
          state = 3;
        } else if( ptn[adr][0]=='L' ){  // L:Loop
          adr = 0;
          state =1;
          goto S00;   // 100ms待たずに再度ステートマシーンに掛ける
        } else if( ptn[adr][0]=='O' ){ // O:出力
          timeUp = ptn[adr][1];
          pwmRef = ptn[adr][2];
          delt_v = 0;
          state = 2;          
        } else if( ptn[adr][0]=='S' ){ // S:sweep
          timeUp = ptn[adr][1];
          delt_v = (ptn[adr][2]-pwmRef)/timeUp;  // 変化量を算出
          state = 2;
        }
      break;

    case 2: // S02:時間カウント
      timeUp--;
      pwmRef = pwmRef + delt_v;
      if(pwmRef<=0){            // 下限、上限リミッタ
          pwmRef = 0;
      } else if(pwmRef>=255){
          pwmRef = 255;
      }
      OCR1A = (unsigned char)pwmRef;                  // O2:analog out (hedd light) 
      if( timeUp <= 0 ){
        adr ++;
        state = 1;  //次のコマンドへ
      }
      break;

      case 3: // stay
      break;

      default:
      break;
  }
}





//---------------------------------------------------------------------------
//ファンクション信号受信のイベント
//FN_0_4とFN_5_8は常時イベント発生(DCS50KはF8まで)
//FN_9_12以降はFUNCTIONボタンが押されたときにイベント発生
//前値と比較して変化あったら処理するような作り。
//---------------------------------------------------------------------------
//extern void notifyDccFunc( uint16_t Addr, FN_GROUP FuncGrp, uint8_t FuncState)
extern void notifyDccFunc(uint16_t Addr, DCC_ADDR_TYPE AddrType, FN_GROUP FuncGrp, uint8_t FuncState)
{
  if ( doing_Resets_Flag == true ) {
    return;
  }


  if( FuncGrp == FN_0_4)
  {
    if( gState_F0 != (FuncState & FN_BIT_00))
    {
      //Get Function 0 (FL) state
      gState_F0 = (FuncState & FN_BIT_00);
    }
    if( gState_F1 != (FuncState & FN_BIT_01))
    {
      //Get Function 1 state
      gState_F1 = (FuncState & FN_BIT_01);
    }
    if( gState_F2 != (FuncState & FN_BIT_02))
    {
      gState_F2 = (FuncState & FN_BIT_02);
    }
    if( gState_F3 != (FuncState & FN_BIT_03))
    {
      gState_F3 = (FuncState & FN_BIT_03);
    }
    if( gState_F4 != (FuncState & FN_BIT_04))
    {
      gState_F4 = (FuncState & FN_BIT_04);
    }
  }

  if( FuncGrp == FN_5_8)
  {
    if( gState_F5 != (FuncState & FN_BIT_05))
    {
      //Get Function 0 (FL) state
      gState_F5 = (FuncState & FN_BIT_05);
    }
    if( gState_F6 != (FuncState & FN_BIT_06))
    {
      //Get Function 1 state
      gState_F6 = (FuncState & FN_BIT_06);
    }
    if( gState_F7 != (FuncState & FN_BIT_07))
    {
      gState_F7 = (FuncState & FN_BIT_07);
    }
    if( gState_F8 != (FuncState & FN_BIT_08))
    {
      gState_F8 = (FuncState & FN_BIT_08);
    }
  }


}

//-----------------------------------------------------
// F4 を使って、メッセージを表示させる。
//上位ビットから吐き出す
// ex 5 -> 0101 -> ー・ー・
//-----------------------------------------------------
void LightMes( char sig ,char set)
{
  char cnt;
  for( cnt = 0 ; cnt<set ; cnt++ ){
    if( sig & 0x80){
      digitalWrite(O1, HIGH); // 短光
      delay(200);
      digitalWrite(O1, LOW);
      delay(200);
    } else {
      digitalWrite(O1, HIGH); // 長光
      delay(1000);
      digitalWrite(O1, LOW);            
      delay(200);
    }
    sig = sig << 1;
  }
      delay(400);
}

//-----------------------------------------------------
// Debug用Lチカ
//-----------------------------------------------------
void pulse()
{
  digitalWrite(O1, HIGH); // 短光
  delay(100);
  digitalWrite(O1, LOW);
}

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0