?>

Hard Copy World

HCW

Q&A

Home > Forum >

Q&A

아두이노 키 프레스 질문좀요!

페이지 정보

작성자 세유니 쪽지보내기 메일보내기 자기소개 아이디로 검색 전체게시물 작성일15-11-14 15:57 조회2,205회 댓글1건

본문

 

오락실에 가보시면 리듬게임 있잖아요. 

리듬에 맞춰서 버튼 누르는 게임인데 

 

그 컨트롤러를 만들고 있습니다. 

 

버튼이나 LED 구현 부분은 다 끝났는데

 

가장 문제가 바로 턴테이블(스크레치) 부분입니다. 

 

보통 원래 오락실에 있는 장비들도 포토인터럽트를 사용해서 

턴테이블을 인식하는데 저는 로터리 엔코더를 이용해서 만드는중인데요

 

아두이노 우노의 펌웨어를 교체하여 우노를 HID 키보드로 인식까지도 다 되는 상태입니다.

 

로터리 엔코더를 돌렸을때 왼쪽 오른쪽 방향 까지 다 받아서 정상 작동 되는걸 확인 했는데

막상 게임을 하려고보니 문제가 생겼습니다.

 

아두이노에서 제공하는 "Encoder" 라이브러리를 이용해서 값을 받는데

소스는 아래와 같습니다.

 

Encoder    Turn_Pin(2,3);

// key buff
uint8_t buf[8] = { 0 };

typedef struct{
    long Old;
    long Now;
    int Wait;
    int Current;
} ENCODER;

ENCODER    Turn = {0,0,0,0};

void EncoderRead(ENCODER* Enc);
void EncoderRead(ENCODER* Enc)
{
  if ((Enc->Old != Enc->Now)) 
  { 
    Enc->Current = millis();
    if (Enc->Old < Enc->Now ) 
    {
      buf[2] = 4;
      Serial.write(buf, 8);
    }
    else if(Enc->Old > Enc->Now)
    {
      buf[2] = 29;
      Serial.write(buf, 8);
    }
  }
  /*
  else if((int)(Enc->Current+Enc->Wait) <= 200)
  {
    releaseKey();
  }
  */
  Enc->Old = Enc->Now;
}


  
void setup()
{
  Serial.begin(9600);
  
  Turn.Wait = 250;
  
  pinMode(4, INPUT_PULLUP);
  pinMode(5, INPUT_PULLUP);
  pinMode(6, INPUT_PULLUP);
  pinMode(7, INPUT_PULLUP);
  pinMode(8, INPUT_PULLUP);
  pinMode(9, INPUT_PULLUP);
  pinMode(10, INPUT_PULLUP);
  pinMode(11, INPUT_PULLUP);
  pinMode(12, INPUT_PULLUP);
  pinMode(13, INPUT_PULLUP);
  
}

void loop()
{
  
  Turn.Now = Turn_Pin.read();
  EncoderRead(&Turn);

}

void releaseKey()
{
  buf[0] = 0;
  buf[2] = 0;
  Serial.write(buf, 8);
}

 

왼쪽과 오른쪽으로 돌릴때 각각 'a' 와 'z' 를 반환 하긴 하는데

키보드에는 지속 누름 기능이 있어서 

버튼을 꾸욱 누르고 있으면 손을 때지 않은것으로 간주되어 지속적으로

한방향이 꾸준히 눌러지는 반면

 

위의 소스대로 하게 되면 매번 로터리엔코더가 돌아갈때마다 

키값을 계속 날려서 왼쪽이든 오른쪽이든 한바퀴 돌리면 순식간에 4~5번의

키 눌렀다 땠다 하는 현상이 나타납니다.

 

지속적으로 같은 방향 으로 돌때는 Serial.write를 안날릴수 있는 방법이 없을까요? 

  

댓글목록

최고관리자님의 댓글

최고관리자 쪽지보내기 메일보내기 홈페이지 자기소개 아이디로 검색 전체게시물 작성일

현재시간 리턴해주는 함수 millis() 사용해서 간격 조정하세요.

unsigned long prev_time = 0
// 로터리 인코더 돌아갔을 때 처리하는 루틴
if(millis() - prev_time < 원하는 시간) {  // 일정시간 지나야만 serial 데이터 전송
    Serial.write();
    prev_time = millis();
}