1

我正在尝试使用示例演示程序从 GPS 获取 NMEA 数据。我将 Delphi 与Aysnc Pro - 版本 5 ( TApdComPort)组件一起使用。我使用OnTriggerAvail事件来捕获 NMEA 字符串。我发现 GPS 单元正在提供不同的数据计数。大多数情况下,它一次提供一个 ASCII 字符。我使用缓冲区字符串捕获所有数据,然后填充所需的 NMEA 语句。在我的演示程序中一切正常。

但是问题出在我将演示代码集成到我的主应用程序中时。我认为我的主程序在接收单个 ASCII 字符时处理得不好。我注意到在调试时,如果接收数据计数(Countfrom OnTriggerEvent)超过 100,则可以填充数据。但是接收数据计数为 1(这种情况更有可能)不会被填充。

请在这里帮助我:

  • 当数据以单个 ASCII 字符连续出现时,有没有更好的方法从串行端口接收数据?
  • 为什么我的演示程序可以完美运行,但不能在我的主应用程序上运行?

这是我的演示代码

procedure TFormMain.btnOpenClick(Sender: TObject);
begin
    Serial_init;
   try
      bufferString := '';
      CarrierOn := false;
      ApdComPort1.Open := True;
      Memo1.Lines.Add('COM port ', IntToStr(ApdComPort1.ComNumber), ' is open');
   except
      on e : EInOutError do
         Memo1.Lines.Add ('Error: ' + e.Message);
   end;
end;

procedure TFormMain.Serial_init;
begin
   ApdComPort1.ComNumber := 4;
   ApdComPort1.Baud := 4800;
   ApdComPort1.DataBits := 8;
   ApdComPort1.Parity := pNone;
   ApdComPort1.StopBits := 1;
end;

const
   NMEA_START = '$';
   NMEA_END_CF = #13;
   NMEA_END_LF = #10;
procedure TFormMain.ApdComPort1TriggerAvail(CP: TObject; Count: Word);
var
   sError : string;
   c: ansichar;
   i: integer;
   CarrierOn: Boolean;
begin
   for i := 1 to Count do
   begin
      c := ApdComPort1.GetChar;
      if c = NMEA_START then
         CarrierOn := True;
      if CarrierOn then // $ has been found collect the data
      begin
         if (c = NMEA_END_CF) then exit;
         if (c = NMEA_END_LF) then
         begin
            sError := '';
            if (PopulateData(bufferString, sError)) then
            begin
               ApdComPort1.FlushInBuffer;
               CarrierOn := false;
               bufferString := '';
               exit;
            end;
            CarrierOn := false;
            bufferString := '';
         end
         else
         begin
            bufferString := bufferString + c;
         end;
      end;
   end;
end;

function TFormMain.PopulateData(const Sentence: string; out ErrorMessage: string): boolean;
begin
   Result := SentenceDecoder('$GPGSV', Sentence);
   if Result then
      Memo1.Lines.Add('Data:' + Sentence); // Display received GSV data
end;

function TFormMain.SentenceDecoder(sentenceName, Sentence: string): boolean;
begin
   Result := Pos(sentenceName, sentence) = 1;
end;

提前致谢

4

0 回答 0