요즘 공부하고 있는 GPS 에 대해서...

 

GPS 와 컴퓨터와 통신을 하기 위해서는 RS232 라는 시리얼  포트를 사용하여 통신을 해야합니다. 그를 위해 보통(내가 현재 속해있는 실험실)은 MFC 를 이용하여 연습을 하던데 나는 이번에 C# 을 이용하여 도전하기로 했습니다.

 

우선 이를 위해 알아야할 가장 중요한것은 바로

 

using System.IO.Ports;

SerialPort sp = new SerialPort();

 

시리얼 통신을 하기 위해서는 몇가지 설정을 해주어야 합니다.

통신할 대상에 맞추어(대상 매뉴얼 참조) 셋팅을 해주면 되는데 이번에 사용할 GPS 의 셋팅은 다음과 같습니다.

 

sp.PortName = label_selected_port.Text;
sp.BaudRate = 9600;
sp.Parity = Parity.None;
sp.DataBits = 8;
sp.StopBits = StopBits.One;

 

다음으로 데이터를 읽기위한 이벤트를 추가해주어야 합니다.

sp.DataReceived += new SerialDataReceivedEventHandler(sp_DataReceived);
//데이터 읽기
void sp_DataReceived(object sender, SerialDataReceivedEventArgs e)
{
      this.Invoke(new EventHandler(ReadGPSData));
}

 

여기서 sp.ReadExisting() 요것이 나오게 되는데 이것은 데이터가 있을데 데이터를(String)을 반환해준다. 이렇게 들어온 데이터를 Parsing 하여 원하는 데이터로 가공하면 시리얼 통신의 목적을 달성 할 수 있습니다.

 

private void ReadGPSData(object s,EventArgs e)
{
    string buff;
    buff = sp.ReadExisting();
    if (buff != null)
    {
        richTextBox_data.Text += buff;

        //데이터 처리하기
        ProcessGPSData(buff);
    }
}

 

바로 이벤트안에 코딩하게 되면 프로그램이 "먹통"이 될 수 있으니 잘 처리해야 합니다. Invoke 를 사용 하면 잘 되는군요^^

 

다음으로 GPS에서 나오는 데이터를 보겠습니다.

$GPGGA,134807.000,3732.6627,N,12701.3549,E,1,04,2.6,39.7,M,19.7,M,,0000*69
$GPGSA,A,3,20,28,17,11,,,,,,,,,6.5,2.6,6.0*3D
$GPGSV,2,1,08,17,60,325,22,28,57,210,34,20,52,066,19,04,32,260,*76
$GPGSV,2,2,08,11,30,066,19,23,10,120,18,01,08,062,,02,00,252,*7A
$GPRMC,134807.000,A,3732.6627,N,12701.3549,E,1.58,329.68,110808,,,A*63

GPS를 통해 나오는 값을 보면 위의 데이터가 화면에 주르르르르륵 나오게 됩니다. 여기서우리가 필요한 정보를 얻기 위해서는 파싱을 해야합니다. 우선 위와 같은 데이터는 NMEA라는 하나의 프로토콜? 이라고 할 수 있습니다.

 

여기서 $GPGGA 가 그리니치 표준시, 경도, 위도 의 정보가 담겨 있다고 하네요

 

다음 포스트에는 요것을 Parsing 해볼까요?

C# Serial Port 통신 - GPS 수신 (2/2)

 

 

신고
Posted by LiveDK

댓글을 달아 주세요

  1. Y 2009.05.23 21:26 신고  댓글주소  수정/삭제  댓글쓰기

    gps 값 받아오는거 자료 찾는 중이었는데,
    잘쓸게요^^

  2. ash84 2010.03.17 15:58 신고  댓글주소  수정/삭제  댓글쓰기

    감사합니다. 잘 보고 갑니다^^

  3. ash84 2010.03.17 18:35 신고  댓글주소  수정/삭제  댓글쓰기

    궁금한데 있는데요.

    ReadExisting()을 하면 쓰레기데이터가 들어오는데, 그건 왜인건가요?

    • DKLEE 2010.03.18 12:10 신고  댓글주소  수정/삭제

      ReadExisting 말고 읽기 위한 매서드가 여러개 존재합니다. Read... 로 검색해서 다른 방법으로 읽어보세요^^ ReadExisting 은 들어 오는 즉시 읽기 때문에 사용하기 까다로운 면이 있습니다.

  4. Jooni 2011.07.12 14:41 신고  댓글주소  수정/삭제  댓글쓰기

    혹시 보실지 모르겠네요. 개인적으로 굳이 Invoke를 사용하는 이유가 잘 이해가 되지 않습니다. Serial Receive를 하는 Event를 띄우는 부분이 MainThread에 있기 때문에 Event를 받아서 처리하는 부분도 MainThread에 접근하기 위해서 Invoke를 사용하는 것인가요?

    저도 처음에 연결 했을 때는 Invoke를 사용하지 않고 Event Handler를 추가했는데 이 때 Close를 할 때 hang이 걸리면서 멈추는 경우가 종종 생겨서 Thread를 이용해서 직접 Read를 계속 호출 하는 방식으로 구현했는데 어느 순간 갑자기 Eventhandler를 사용하였을 때도 정상 종료가 가능해져서 계속 쓰고는 있지만 굳이 Invoke를 사용하신 의도가 궁금해서 댓글 달아 봅니다.

    • LiveDK 2011.07.13 09:27 신고  댓글주소  수정/삭제

      안녕하세요:)
      Invoke를 사용했던 이유는 아마도 form에 접근하기 위해서였던거 같네요 스레드에서 돌고 있다가 form에 접근하면 에러가 나서 그랬었는데, jooni님께서 하신방법으로도 잘 동작하신다면 상관 없을거 같네요^^

  5. 아퀴 2011.08.09 16:16 신고  댓글주소  수정/삭제  댓글쓰기

    sp.PortName = label_selected_port.Text;
    이 부분은 무엇을 뜻하는 건가요
    그대로 쳐보면 현재 컨텍스트에 없다고 나오는데 ~

    궁금합니다 ~

  6. 박재범 2011.08.19 08:01 신고  댓글주소  수정/삭제  댓글쓰기

    안녕하세요. 글 잘 보았습니다.

    gps 수신 모듈에서 나오는 데이터를 받아보니 쓰레기 데이터가 나오더라구요..

    위에서 알려주신 ReadGPSData() 대로 하면

    바로 gps 수신 데이터가 나오는건가요?

    아니면
    ProcessGPSData(buff);
    라는 함수를 거쳐야 하는건가요?

    • LiveDK 2011.08.21 11:26 신고  댓글주소  수정/삭제

      ReadGPSData()에는 GPS에서 컴퓨터의 시리얼포트로 전송된 (가공되지 않은) 데이터들이 들어 올것입니다. 이러한 데이터들을 알맞게 처리하는것은 본인 마음입니다. 저는 ProcessGPSData(buff); 라는 함수를 따로 만들어서 처리한것 뿐입니다.
      GPS로 부터 데이터가 들어온다면 거의 성공하신것이고 이를 잘 파싱하여 위도 경도를 뽑아 오면 됩니다^^

  7. ghd 2013.07.17 04:49 신고  댓글주소  수정/삭제  댓글쓰기

    좋으면 좋고 싫으면 싫은 거지, 뭐가 이렇게 어렵고 복잡하냐구

  8. 2013.07.23 21:51  댓글주소  수정/삭제  댓글쓰기

    비밀댓글입니다



티스토리 툴바