tagCANDY CGI VBレスキュー(花ちゃん)の Visual Basic 6.0用 掲示板 [ツリー表示へ]   [Home]
一括表示(VB6.0)
タイトルmscPortの同期処理についての質問
記事No14382
投稿日: 2010/01/18(Mon) 22:30
投稿者プロペラ
はじめまして。
色々調べた結果、解決できなかったためこちらに投稿します。
vb6にて2つの計測器の擬似的な同期処理を行うと思っています。

仕様として
計測器A...PC側から命令をせず、0.5秒〜1秒単位で受信データを送信してくる。
計測器B...PC側から命令(VAL?)をすることにより、受信データを送信してくる。

手順
計測器Aより受信データの取得(onCommイベント)
→PC側から計測器Bへ命令を送る(VAL?)
→計測器Bより受信データの送信
→計測器Bより受信データの取得(onCommイベント)
→PC側にて2つの測定器のグラフ表示・Excelへ書き込み等

問題として
計測器Bへ命令を送るところまでは動作するのですが、計測器Bの受信データが変数に格納するのを参照するのが遅い(OnCommイベントがすぐに発生しない)ことにより、計測器Bの受信データが、1つ前のデータとなってしまっていて困っています。

要するに計測器Bの受信データの格納を割り込んで行いたいということです。
また、計測器Bが「VAL?」と命令してデータが送り返してくる時間は0.05(s)程度でくるので送られていないということは、ないかなと思います。

どんな些細なことでもいいので、アドバイス等ご教授願います。

以下にコードを記述します。(コード内の不必要な部分は省略してます)
※計測器AがPort2で計測器BがPort1です、紛らわしくてすいません。

'   計測器A(mscPort2)のOnCommイベント
Private Sub mscPort2_OnComm()

    Call mscPort2_Measure

End Sub    

'   計測器A(mscPort2)の計測イベント
Private Static Sub mscPort2_Measure()

    '   CommEventプロパティに対する各処理
    Select Case mscPort2.CommEvent

        '   イベントメッセージ
        '   CD ラインの状態が変化しました
        Case comEvCD
        '   CTS ラインの状態が変化しました
        Case comEvCTS
        '   DSR ラインの状態が変化しました
        Case comEvDSR
        '    リング インジケータの状態が変化しました
        Case comEvRing
        '   RThreshold プロパティで指定された数のバイトを受信しました
        Case comEvReceive

            '   エラーが発生しても継続させる
            On Error Resume Next

            '   受信データの取得
            Port2VarBuffer = mscPort2.Input
            TotalValue = TotalValue & Port2VarBuffer

            '   受信時刻の取得
            Port2ReceiveTime = Format$(Time, "hh:nn:ss")

                '   校正器に「VAL?」命令を出力する
                '   VAL?を通信ポートへ送信
                '   最後にターミネータを付加する。
                mscPort1.Output = "VAL?" & Chr(&HA)
                
                If g_CharMeasureFlag = 0 Then
                    Call mscPort1_Measure(GapPreGainData, QuiPreGainData, TempGainData, TransformGapPreData, QuiPreData_10, TransformTempData, Port2ReceiveTime)
                ElseIf g_CharMeasureFlag = 1 Then
                    Call mscPort1_Measure(GapPreGainData, QuiPreGainData, TempGainData, GapPreData_10, QuiPreData_10, TempData_10, Port2ReceiveTime)
                End If

        End If

        '   受信データの初期化
        Port2VarBuffer = ""
        TotalValue = ""
        NewValue = ""

        '   送信バッファに SThreshold プロパティで指定された数のバイトが入っています。
        Case comEvSend
        '   入力ストリーム内に EOF 文字が検出されました。
        Case comEvEOF

        '   エラーメッセージ
        Case comEventBreak
            MsgBox "中断信号が受信されました。", vbExclamation, "通信エラー"
        Case comEventFrame
            MsgBox "フレーム エラーです。", vbExclamation, "通信エラー"
        Case comEventOverrun
            MsgBox "データが失われました。", vbExclamation, "通信エラー"
        Case comEventRxOver
            MsgBox "受信バッファがオーバーフローしました。", vbExclamation, "通信エラー"
        Case comEventRxParity
            MsgBox "中パリティ エラーです。", vbExclamation, "通信エラー"
        Case comEventTxFull
            MsgBox "送信バッファがいっぱいです。", vbExclamation, "通信エラー"
        Case comEventDCB
            MsgBox "デバイス コントロール ブロック (DCB) が取得される予期しないエラーです。", vbExclamation, "通信エラー"

        Case Else
            MsgBox "未定義のエラーが発生しました。", vbExclamation, "通信エラー"
    End Select

End Sub

'   計測器Bの受信イベント
Private Static Sub mscPort1_Measure(GapPreGainData As Integer, QuiPreGainData As Integer, TempGainData As Integer, GapPreData As Double, QuiPreData As Double, TempData As Double, Port2ReceiveTime As Date)
                  
    '   CommEventプロパティに対する各処理
    Select Case mscPort1.CommEvent
        '   イベントメッセージ
        '   CD ラインの状態が変化しました
        Case comEvCD
        '   CTS ラインの状態が変化しました
        Case comEvCTS
        '   DSR ラインの状態が変化しました
        Case comEvDSR
        '   リング インジケータの状態が変化しました
        Case comEvRing
        '   RThreshold プロパティで指定された数のバイトを受信しました
        Case comEvReceive

            '   受信データ・時刻の取得
            Port1VarBuffer = mscPort1.Input
            PreDataStr = PreDataStr & Port1VarBuffer
            Port1ReceiveTime = Format$(Time, "hh:nn:ss")
        
            '   文字数取得
            Port1CharCount1 = InStr(PreDataStr, vbCr)
            If Port1CharCount1 Then
            
                '   必要な要素のみ表示(kPa情報のみ)
                Port1CharCount2 = InStr(PreDataStr, ",")
                PreDataStr = Left$(PreDataStr, Port1CharCount2 - 1)
                PreData = Val(PreDataStr)
                PreData = Format(PreData, "0.000")
                
                '   受信データの初期化
                PreDataStr = ""
                
                Call Calculate(GapPreGainData, QuiPreGainData, TempGainData, PreData, GapPreData, QuiPreData, TempData, Port1ReceiveTime, Port2ReceiveTime)
                
            End If
                
        '   送信バッファに SThreshold プロパティで指定された数のバイトが入っています
        Case comEvSend
        '   入力ストリーム内に EOF 文字が検出されました
        Case comEvEOF
        
        '   エラーメッセージ
        Case comEventBreak
            MsgBox "中断信号が受信されました。", vbExclamation, "通信エラー"
        Case comEventFrame
            MsgBox "フレーム エラーです。", vbExclamation, "通信エラー"
        Case comEventOverrun
            MsgBox "データが失われました。", vbExclamation, "通信エラー"
        Case comEventRxOver
            MsgBox "受信バッファがオーバーフローしました。", vbExclamation, "通信エラー"
        Case comEventRxParity
            MsgBox "中パリティ エラーです。", vbExclamation, "通信エラー"
        Case comEventTxFull
            MsgBox "送信バッファがいっぱいです。", vbExclamation, "通信エラー"
        Case comEventDCB
            MsgBox "デバイス コントロール ブロック (DCB) が取得される予期しないエラーです。", vbExclamation, "通信エラー"

        Case Else
            MsgBox "未定義のエラーが発生しました。", vbExclamation, "通信エラー"
    End Select

End Sub

以上です。
よろしくお願い致します。

[ツリー表示へ]
タイトルRe: mscPortの同期処理についての質問
記事No14383
投稿日: 2010/01/19(Tue) 09:56
投稿者GOD
>                 '   校正器に「VAL?」命令を出力する
>                 '   VAL?を通信ポートへ送信
>                 '   最後にターミネータを付加する。
>                 mscPort1.Output = "VAL?" & Chr(&HA)
>                
>                 If g_CharMeasureFlag = 0 Then
>                     Call mscPort1_Measure(GapPreGainData, QuiPreGainData, TempGainData, TransformGapPreData, QuiPreData_10, TransformTempData, Port2ReceiveTime)
>                 ElseIf g_CharMeasureFlag = 1 Then
>                     Call mscPort1_Measure(GapPreGainData, QuiPreGainData, TempGainData, GapPreData_10, QuiPreData_10, TempData_10, Port2ReceiveTime)
>                 End If
>
計測器に VAL? を送った後、mscPort2_Measure処理内で mscPort1_Measure 関数を呼び出
しているみたいですが、mscPort1_Measure 関数が呼び出された時に本当に受信している
のですか。(そこそこの性能を持ったPCを使用していれば、数バイトのデータを送信バ
ッファに格納、IF文判定、関数呼び出しで 50msも経過しないと思うのですが。仮に50ms
経過するPCで開発を行っているのだとしてもPC性能に左右されるコードは使いべきで
はないですよ。)

mscPort1_Measure 関数を呼び出しを mscPort1_OnCommでやった方が良いですよ。

[ツリー表示へ]
タイトルRe^2: mscPortの同期処理についての質問
記事No14397
投稿日: 2010/01/20(Wed) 07:34
投稿者プロペラ
> 計測器に VAL? を送った後、mscPort2_Measure処理内で mscPort1_Measure 関数を呼び出
> しているみたいですが、mscPort1_Measure 関数が呼び出された時に本当に受信している
> のですか。(そこそこの性能を持ったPCを使用していれば、数バイトのデータを送信バ
> ッファに格納、IF文判定、関数呼び出しで 50msも経過しないと思うのですが。仮に50ms
> 経過するPCで開発を行っているのだとしてもPC性能に左右されるコードは使いべきで
> はないですよ。)
>
> mscPort1_Measure 関数を呼び出しを mscPort1_OnCommでやった方が良いですよ。

迅速な返信ありがとうございます。
GODさんの通り+計測器Aの計測データをグローバル変数にて格納して
計測器BのOnCommイベントが発生後、2つの測定データを引数で持たせたら上手く同期が取れました。

ありがとうございました。

[ツリー表示へ]