• 締切済み

VS.NET2005 C#にてSerialPort受信されたときのイベントについて質問

Visual Studio.NET2005ProにてSerialPort接続アプリケーションを開発しております。 受信が来たときのイベント DataReceived のところで、受信された文字列をテキストボックスへ表示させるということを行いたいのですが、エラーが出てしまいます。 ちなみにプログラムはこうです。 private void serialPort_DataReceived(object sender, System.IO.Ports.SerialDataReceivedEventArgs e) { //シリアルポートからデータを受信するたびに発生する textBox_all_in.Text = (string)serialPort.ReadByte(); } それで、エラーは エラー 1 型 'int' を型 'string' に変換できません。 このように出てしまいました。プログラミング初心者で、つまずいてしまいどうすればよいのかわからなく困っております。アドバイスよろしくお願いします。

みんなの回答

回答No.2

http://www.atmarkit.co.jp/fdotnet/dotnettips/312ctrlinvoke/ctrlinvoke.html スレッドエラーは、こんな理由だそうです。

参考URL:
http://www.atmarkit.co.jp/fdotnet/dotnettips/312ctrlinvoke/ctrlinvoke.html
basic01
質問者

補足

書き込みありがとうございます。 textBox_all_in.Text = serialPort.ReadByte().ToString(); これを Invoke(new FocusDelegate(textBox_all_in.Text = serialPort.ReadByte).ToString); に書き換えてみましたが、 型または名前空間名 'FocusDelegate' が見つかりませんでした。using ディレクティブまたはアセンブリ参照が不足しています メソッド グループ 'ReadByte' を非デリゲート型 'string' に変換することはできません。このメソッドを呼び出すことはできません。 と、2つエラーが出ました。いろいろ考えて、自分でも調べてみたのですが解決できません・・・ヒントをいただけないでしょうか?

  • anmochi
  • ベストアンサー率65% (1332/2045)
回答No.1

 シリアルポートの問題ではないね。C#言語の話だ。  textBox_all_in.Text = (string)serialPort.ReadByte();  ↓  textBox_all_in.Text = serialPort.ReadByte().ToString();  これをまず試していただきたい。で、エラーは出なくなるが、おそらく質問者が満足する回答ではないと思う。ReadByte()は、入ってきたデータの8ビット値をintで取るものなので、文字列じゃないわけだ。  それに関してはまた別質問であげた方が良いんじゃないかな。シリアルポートうんぬんの時点で問題の焦点がぼやけてると思う。

basic01
質問者

補足

回答ありがとうございます。 初心者なのでなかなかまだわからないことだらけでした。僕は組み込み用Cしかろくに書いたことがなく文字列を扱うっていうのは初めてなものでしっくりこなくうまく扱いこなすことができませんでした。シリアルポートを扱うことよりもまず先に変数型について理解を深めておかなければならないというのは自覚はしております。 ちなみに、ソースを書き直してビルドしましたが、エラーは出なかったもののデバック中文字を受信すると 有効ではないスレッド間の操作: コントロールが作成されたスレッド以外のスレッドからコントロール 'textBox_all_in' がアクセスされました。 と出ましたことを報告いたします。

関連するQ&A

  • .NETの SerialPortクラスでデータ受信イベントを処理するには?

    こんばんは。いつもお世話になっております。 Visual C++ 2005でSerialPortクラスを使ってシリアル通信をしたいのですが、データ受信イベントハンドラをどのように扱えばよいか分からず困っていますのでご教示ください。 HelpやMSDN、インターネット上で検索をして見つかるのはC#の例ばかりで、C++でどのように記述するのかが見つかりませんでした。 イベントやデリゲートなど、.NETで導入された(であろう)概念が出てきたり、^(ケット)記号が出てきたりと戸惑うことも多いのですが、きっと serialPort1->DataReceived += gcnew イベントハンドラを登録; // イベントハンドラの本体 private: System::Void serialPort1_DataReceived(System::Object^ sender, System::EventArgs^ e){ ほげほげ; } みたいな感じで書くのではないかと予想しています。 Visual Basic 6.0 でのシリアル通信はずっと使ってきました。 C/C++は使い始めて10年弱、C++/CLIは未経験です。(似て非なる言語?) よろしくお願いします。

  • VB2010 シリアル受信した情報を表示する

    VB2010 シリアル受信した情報を表示する フォームが表示されたらポートを開けてテキストボックスに文字を表示させたいです。 送られてくる情報はSTXとETXで挟まれた数十文字のアスキー文字です。 フォーム表示中は、teratermやハイパーターミナルで接続不可エラーが出ますし その逆でteratermやハイパーターミナルで接続している時にはcomポートエラーが出ます。 teratermやハイパーターミナルではシリアルで受信した文字が表示されています。 そのような状況で下記、シンプルなコードを作りましたが表示されません。 テキストボックスが何も変化しない状態です。なんでもいいので、テキストボックスに受信した情報を出してみたいです。 http://msdn.microsoft.com/ja-jp/library/cc720852.aspx を参考に受信部分に使っています。 Public Class Form1 Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load Call SerialPort1.Open() End Sub Delegate Sub AddDataDelegate(ByVal str As String) Private Sub AddData(ByVal str As String) TextBox1.Text = TextBox1.Text + str End Sub Private Sub SerialPort1_DataReceived(ByVal sender As Object, ByVal e As System.IO.Ports.SerialDataReceivedEventArgs) Handles SerialPort1.DataReceived Dim strDataReceived As String Dim add As New AddDataDelegate(AddressOf AddData) Try strDataReceived = SerialPort1.ReadLine Catch ex As Exception strDataReceived = ex.Message End Try TextBox1.Invoke(add, strDataReceived) End Sub End Class

  • vb2005で受信関数を以下の作成しています。

    vb2005で受信関数を以下の作成しています。 Private Sub r_SerialPort1_DataReceived(ByVal sender As Object, _  ByVal e As System.IO.Ports.SerialDataReceivedEventArgs) _  Handles SerialPort1.DataReceived  Dim tmp As Integer  Try   tmp = SerialPort1.BytesToRead '受信バイト数取得 SerialPort1.Read(s_RxBuff, s_RxCont, tmp) 'データ読込み s_RxCont = s_RxCont + tmp '受信バイト数更新  Catch ex As Exception s_Status = c_ErrTRP 'ポートエラー(受信) End Try End Sub この関数で割込みが入るのですが、tmp=の所でbreakし読出そうとしてSerialPort1をウォッチすると、 "ポートは閉じられています"と表示されていて、Catch方向に進むのですが、何故こんなことが起こるのでしょうか? 宜しくお願いします。

  • VBでシリアル通信がうまくいきません

    VisualBasicのシリアルポートメソッドを使い、RS232-C通信を試そうとしている初心者です。 現在、別のPCからTeratermより文字を送り、自分のPCで受信結果を得ようとしているのですが 別PCから単発で文字を送っても、自分のPCでは反応せず キーボードを押しっぱなしにすると、自分のPCのウィンドウに受信結果が表示されます。 一体、何が原因なのでしょうか? さっぱり、わからず途方に暮れています。 下記にソースコードを記載しますので、詳しい方は教えて下さると幸いです。 ------------------------------------------------------------------------ Public Delegate Sub MyDelegate(ByVal intData As Integer) Private Sub AddData(ByVal str As String) TextBox1.Text = str End Sub Private Sub SerialPort1_DataReceived(ByVal sender As Object, ByVal e As System.IO.Ports.SerialDataReceivedEventArgs) Handles SerialPort1.DataReceived Dim dlgByte As MyDelegate = New MyDelegate(AddressOf AddData) Dim ByteRead(SerialPort1.BytesToRead - 1) As Byte SerialPort1.Read(ByteRead, 0, SerialPort1.BytesToRead) For i As Integer = 0 To ByteRead.Length - 1    Me.Invoke(dlgByte, ByteRead(0)) Next End Sub ------------------------------------------------------------------------

  • 'Button1を押したらポートオープン

    'Button1を押したらポートオープン Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click 'シリアルポートを設定。 SerialPort1.PortName = SerialPortComboBox.Text SerialPort1.BaudRate = SerialBpsComboBox.Text Select Case SerialParityComboBox.Text Form3.SerialPort1.Parity = IO.Ports.Parity.None 'データ長 SerialPort1.DataBits = SerialDataBitsComboBox.Text 'RTSラインを有効にする SerialPort1.RtsEnable = True '送信タイムアウト SerialPort1.WriteTimeout = 3000 Try 'ポートをオープン SerialPort1.Open() 'いざ送信 'SerialPort1.Write(Chr(&HC)) 'ケーブルが外れた場合などのタイムアウトエラーなら、 Catch ex As Exception MsgBox(ex.Message, MsgBoxStyle.Critical, "シリアル通信エラー") SerialPort1.Close() Exit Sub End Try '送信バッファが空になるまで待って、 While SerialPort1.BytesToWrite > 0 My.Application.DoEvents() End While ''''''''''''文字送信 'シリアルポート送信データをSJISに指定 SerialPort1.Encoding = System.Text.Encoding.GetEncoding(932) Dim Settei As String '送信文字代入 Settei = "A.1=" & vbCrLf 'いざ送信 SerialPort1.Write(Settei) '送信バッファが空になるまで待って、 While SerialPort1.BytesToWrite > 0 My.Application.DoEvents() End While End Sub '文字受信 Private Sub SerialPort1_DataReceived(ByVal sender As Object, ByVal e As System.IO.Ports.SerialDataReceivedEventArgs) Handles SerialPort1.DataReceived Dim strDataReceived As String Dim add As New AddDataDelegate(AddressOf AddData) Try strDataReceived = SerialPort1.ReadLine Catch ex As Exception strDataReceived = ex.Message End Try TextBox1.Invoke(add, strDataReceived) End Sub ///////// 文字を送信した後に相手から帰ってきます。 送信した後の受信の部分ですが、これで正しいか教えて頂きたいです。

  • visual c# 2010 シリアル通信アプリ

    http://www.kana-soft.com/tech/sample_0007.htm のサイトを参考に、マイコンとのシリアル通信評価に使うPCのアプリケーションを visual c# 2010で作っています。 一応データを受け取るようになったのですが、 63H 62H 61H 00H (アスキーコードだと"cba<null>") というデータを送っているはずなのですが、 扣a というデータが受信されてしまいます。 正しく受信するにはどうすれば良いでしょうか。 (該当していそうな部分のソースです) : : /****************************************************************************/ /*! * @brief データ受信が発生したときのイベント処理. * * @param [in] sender イベントの送信元のオブジェクト. * @param [in] e イベント情報. * * @retval なし. */ private void serialPort_DataReceived(object sender, System.IO.Ports.SerialDataReceivedEventArgs e) { //! シリアルポートをオープンしていない場合、処理を行わない. if (serialPort1.IsOpen == false) { return; } try { //! 受信データを読み込む. string data = serialPort1.ReadExisting(); //! 受信したデータをテキストボックスに書き込む. Invoke(new Delegate_RcvDataToTextBox(RcvDataToTextBox), new Object[] { data }); } catch (Exception ex) { MessageBox.Show(ex.Message); } } /****************************************************************************/ /*! * @brief 受信データをテキストボックスに書き込む. * * @param [in] data 受信した文字列. * * @retval なし. */ private void RcvDataToTextBox(string data) { //! 受信データをテキストボックスの最後に追記する. if (data != null) { rcvTextBox.AppendText(data); } }

  • SerialPortのDataReceivedイベントについて

    Visial Basic 2005 にて SerialPort コンポーネントを使ったアプリを作っています。 当初、Microsoft のサンプルを参考に SerialPort1.ReadLine でデータを受信していたのですが、この方法だとバッファ内から再度同じデータを受信してしまうらしく、新しいバッファからデータを受信しないとイベントが発生する毎に古いデータを読み取ってしまいます。 そこで調べていたところ、Microsoft のフォーラムで以下のような Visual C# のソースを見つけました。 (以下引用) > if (serialPort1.BytesToRead > 0) > { > // 受信バッファからデータを取得 > byte[] b = new byte[serialPort1.BytesToRead]; > Read(b, 0, b.Length); > } まだ Visial Basic 初心者なもので Byte 型の扱い方や上記ソースは Visial Basic でどのように書けばよいのかわかりません。 どなたかご教授ください。 よろしくお願いいたします。

  • シリアル受信データをファイルに書き出したい

    マイコンとPCをCOMポートで通信し、受信データをファイルに書き出したいのです。 やってみたこと1.と2.の間を埋める技術についてアドバイスをお願いします。 1.キーボード入力したテキストボックスの内容をファイルに書き出す ⇒書けました、OK     Dim xxx As New System.IO.StreamWriter("e:xxx.txt", False, System.Text.Encoding.Default) xxx.WriteLine(TextBox1.Text) xxx.Close() 2.サンプルコードでシリアル通信 ⇒受信データがテキストボックスに表示されました、OK     以下サイトを参考に勉強中、テキストボックス部分を抜粋させて頂きます     (http://www.kana-soft.com/tech/sample_0008_4.htm#1) 3.2.で表示されたテキストボックスの内容を、1.のように書き出したいのですが   上手くいきません。'■から'■間に xxx.WriteLine(RcvTextBox.Text) 書いてみましたが   e:xxx.txtは作成されません。delegate、invokeの理解不足が原因かと思うのですが、   調べ回るうちに・・・限界みたいです。(^_^;) (抜粋) '===== Private Delegate Sub Delegate_RcvDataToTextBox( data As String ) '===== Private Sub SerialPort1_DataReceived(ByVal sender As System.Object, ByVal e As System.IO.Ports.SerialDataReceivedEventArgs) Handles SerialPort1.DataReceived Try '受信データを読み込む. Dim data As String data = SerialPort1.ReadExisting() '受信したデータをテキストボックスに書き込む. Dim args(0) As Object args(0) = data Invoke(New Delegate_RcvDataToTextBox(AddressOf Me.RcvDataToTextBox), args) Catch ex As Exception MsgBox( ex.Message ) End Try End Sub '===== Private Sub RcvDataToTextBox( data As String ) '受信データをテキストボックスの最後に追記する. If IsNothing( data ) = False Then RcvTextBox.AppendText( data ) End If '■     Dim xxx As New System.IO.StreamWriter("e:xxx.txt", False, System.Text.Encoding.Default) xxx.WriteLine(RcvTextBox.Text) xxx.Close()     '■ End Sub ===== 以上、駄目出しをよろしくお願いします。

  • (VC++)シリアル通信について

    OS:Windows7 開発環境:VisualStudio2010 言語:C++ 機器:カードリーダ 接続:RS-232C VisualStudio2010にて、シリアル通信を行うプログラムを作成しています。 VisualStudioのヘルプや、いくつかのWebページを参考に、送信を行うところまではできています。 しかし、受信ができているのか、もしくは受信した内容が表示できていないのか分かりませんが、受信が確認できません。 送信はカードリーダが動くので分かりやすいのですが、受信は表示できないと確認できないためこのような状態です。 カードリーダの仕様は、あるASCIIコードを送るとカードが送られ、エラーステイタスコードが返ってきます。正常にカードが送られた場合は、またASCIIコードを送ると、読み取ったカードの情報がでてきます。(シリアル通信をテストするプログラムでは送信受信共に成功しています。) (送信)は、こちらが送ったもので、それ以外は受信した結果です。 ---------------以下その時の結果--------------- 3f 0d (送信) 30 10 45 30 31 32 30 30 38 0d (送信) 32 0d 33 59 0d 30 0d 31 59 0d 32 59 0d 33 0d 30 0d 31 0d ---------------------------------------------- C++のプログラムは以下の様になっています。 上記の結果でいうと、3f、0dを送り30を受け取るというところです。3f、0dでカードが送られ、30(正常終了)という結果を受け取ります。この結果をテキストボックスに表示したいと考えています。現在は、カードは送られるものの、30(もしくは他のエラーステイタスコード)という結果を表示することができません。 private: System::Void button_start_Click(System::Object^ sender, System::EventArgs^ e) {  serialPort1->Open();  serialPort1->Write(x3f); //defineにて定義(中身は?[0x3f])  serialPort1->Write(x0d); //defineにて定義(中身はCR[0x0d])  serialPort1->Close(); } delegate void SerialDataRecievedDelegate(String^ recvData); private: void SerialDataRecieved(String^ recvData) {  textBox1->Text = recvData; //確認するためにtextBox1に結果を表示 } private: System::Void serialPort1_DataReceived(System::Object^ sender, System::IO::Ports::SerialDataReceivedEventArgs^ e) {  SerialDataRecievedDelegate^ dlgte = gcnew SerialDataRecievedDelegate( this, &CardReader::Form1::SerialDataRecieved );  String^ RecievedData = serialPort1->ReadExisting();  //1バイトずつ受信  if(serialPort1->IsOpen == true) //シリアルポートが開いているか確認  {   COMRevieveBuffer = COMRevieveBuffer + RecievedData; //受信バッファに追加   if(RecievedData == "\r" ) //改行コード検出   {    RecievedData = RecievedData + "\n";    COMRevieveBuffer = COMRevieveBuffer + RecievedData;    //受信した一行をテキストボックスに転送    this->Invoke(dlgte, COMRevieveBuffer);    COMRevieveBuffer = "";   }   //エコーを返す   serialPort1->Write(RecievedData);  } } C言語でのプログラム作成はしていたのですが、VisualStudioやC++でのプログラム作成は初めてです。 ソースに変な点が多々あるとは思います。 ご教授お願いします。

  • C# シリアル通信でデータ受信時の欠損について

    Visualstudio 2013 を使用して C# で開発を行っています。 SerialPort Classを使用してデータの送受信をするプログラムを作成しているのですが、 非同期でデータを受信する際にどうしてもうまくデータを取得出来ません。 5Byteのデータは正常に取得できるのですが、 その直後にくる40Byteのデータは、真ん中あたりの10数Byteや最後の10数Byteしか取れません。 serialPort.DataReceived に登録したイベント関数の中身です。 -------------------------------------------------------------------------------------- private void _serialPort_DataReceived(object sender, SerialDataReceivedEventArgs e) { bytesRead = 0; // Initialize a buffer to hold the received data byte[] buffer = new byte[this.serialPort.ReadBufferSize]; try { bytesRead = this.serialPort.Read(buffer, 0, buffer.Length); if (true == serialPort.IsOpen) { serialPort.DiscardInBuffer();//受信バッファをクリアする } } catch (Exception ex) { DataLog.Exception(ex); } //派生クラス用の処理 DeviceClassEventArgs _DeviceClassEventArgs = new DeviceClassEventArgs(buffer, bytesRead); DeviceClassEvent(this, _DeviceClassEventArgs); } -------------------------------------------------------------------------------------- ネットの情報を参考に、 ReceivedBytesThreshold の値を期待するデータ量に逐一変えることで とりあえず正常に取ることが出来たのですが、これでいいのでしょうか? 期待するデータ量がわからなかった場合は使えないのかなとも思います。 データが欠損してしまう理由、 上記の対処法以外の一般的な対処法など有りましたら教えて下さい。 その他参考になるページ等ありましたら教えていただけると大変助かります。

専門家に質問してみよう