2012-01-29 3 views
1

저는 오래된 Sony Ericsson 전화를 사용하여 AT 명령을 쓰고 읽는 작은 구성 요소로 작업하고 있습니다. 전화로 /에서 보내고 쓰는 것이 전혀 문제가되지 않지만 SendATCmd 함수를 일시 중지하고 COM 포트 구성 요소가 알림 이벤트로 알림을 보내고 SendATCmd 함수를 다시 시작할 때까지 기다릴 수 있기를 바랍니다.루프에서 더 많은 데이터를 보내기 전에 COM 포트 수신 이벤트를 기다리는 방법

시나리오 : 전화에서 SMS 메시지의 수를 얻고 싶습니다. 일반적으로 나는 그저 전화를 말할 것입니다 : 이봐, 얼마나 많은 SMS 메시지가 있니? 전화가 알림 이벤트에서 회신합니다. 그게 다 좋다.

하지만 제가 정말하고 싶은 것은 SendATCmd의 코드는 다음과 같습니다

if SendATCmd('CountSMS')>0 then 
    for 0 to SMSCount do 
    AddSMSToList; 

같은 : 나는 잠시 루프를 사용하여 시도했다

function TSE_Z1010.SendATCmd(Cmd: string): TATResult; 
begin 
    fCOMPort.PutString(Cmd); //Sending AT command 

    //Here is where I would like to pause this function 
    //wait for the fCOMPort to notify me when data is available 
    //and then resume this function again. 

    result:=fTMPATResult; 

end; 

, 일시 정지, 등 등 ,하지만 한 가지를 제외하고는 아무 것도 작동하지 않습니다. 그 때 멈춤이 있어야하는 ShowMessage를 넣습니다. ShowMessage가 내부적으로 어떻게 작동하는지 모르지만 while 루프와 일시 중지처럼 프로그램을 중단시키지 않는 것으로 보입니다.

==================

수정 됨.

내가 할 일은 uses 절에 Forms를 추가 한 다음 fTMPATResult.Full = false를 추가하는 것입니다. Application.ProcessMessages; 내가 그 절차를 일시 중지하고 싶은 부분에서.

"fTMPATResult"는 수신 COM 포트 데이터가 구성 요소 내에 전역으로 저장되는 변수입니다.

+4

답변이있는 경우 질문에 대한 편집이 아닌 답변으로 추가하십시오. –

+0

그것은 내 자신의 질문에 대한 답변을 추가하기에 충분한 점수가 없다고 말했습니다. – xaid

+0

사용하는 직렬 통신 구성 요소 (fCOMPort) 란 무엇입니까? – menjaraz

답변

1

AsyncPro에는이 (ontriggerdata)에 대한 몇 가지 솔루션이 있지만 이벤트 기반이므로 코드를 읽기/이해하기가 어렵습니다. 여기

은 (레미 제안처럼) AsyncPro와 SendAndWaitForResponse입니다 :

TForm1 = class(TForm) 
... 
private 
    IOEvent   : THandle; // used for IO events 
    IORx    : string; 
    Comport   : TapdComport; 
... 


procedure TForm1.ComportTriggerAvail(CP: TObject; Count: Word); 

var i  : integer; 

begin 
for i:=1 to Count do 
    IORx:=IORx+Comport.GetChar; 
SetEvent(IOEvent); 
end; 

function TForm1.SerialSAWR(tx : string; TimeOut : integer) : boolean; 
begin 
Result := False; 
try 
    IORx := ''; // your global var 
    ResetEvent(IOEvent); 
    Comport.PutString(tx); 
    Result := WaitForSingleObject(IOEvent, TimeOut) = WAIT_OBJECT_0; 
except 
    on E : Exception do 
    // dosomething with exception 
end; 
end; 

// constructor part 
IOEvent := CreateEvent(nil, True, False, nil); 
// destructor part 
if IOEvent <> 0 then 
    CloseHandle(IOEvent); 

가장 좋은 방법은 그래서 당신의 GUI가 차단되지 않습니다 처신와 스레드를 생성하는 것입니다. Asyncpro와 함께 여러 가지 응용 프로그램을이 방법으로 사용하면 매력처럼 작동합니다.

+0

생성자 부분과 소멸자를 넣을 위치를 이해할 수 없습니다. ( – ELCouz

+0

@ElCouz : 이에 따라 달라집니다. 양식을 사용하는 경우 OnCreate 이벤트와 OnDestroy 이벤트가 좋습니다. – whosrdaddy

+0

고마워! :) 또 다른 문제는 .. .이 코드에서 RX 부분은 어디에도 보이지 않는다? send와 get (응답을 기다리는) 같은 명령을 찾고 있었는데 응답을 보내고 기다리는 것을 볼 수 있지만 응답을 캡처하지는 않는다. – ELCouz

0

언제든지 Application.ProcessMessages()으로 전화해야 할 때마다 코드 디자인을 재고해야합니다. 두 배로 루프에서 호출 할 때.

Asynch Pro의 작동 방식을 모르지만 Win32 API에는 사용자가 요구하는대로 WaitCommEvent() 함수가 있습니다. 이 함수를 호출하여 직렬 포트에 원하는 이벤트 알림을 요청한 다음 WaitForOverlappedResult() 또는 WaitForSingleObject()을 사용하여 직렬 포트가 겹쳐진 모드로 작동하는지 여부에 따라 실제로 발생하는 이벤트를 기다릴 수 있습니다. 메시지 처리가 필요하지 않습니다. Asynch Pro가 어떻게 든 그 기능을 드러내지 않는다면 놀랄 것입니다.