当前位置: 首页 > article >正文

C# WPF 串口通信

C# WPF 串口通信

  • 安装依赖库

安装依赖库

  • System.IO.Ports
    在这里插入图片描述
    在这里插入图片描述
using System.Diagnostics;
using System.IO.Ports;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Markup.Localizer;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;

namespace GasAlarmFactoryTools
{
    struct TestInfoData {
        public string dev_uuid;
        public string dev_simcard;
        public string private_data;
        public string datetime;
    };

    /// <summary>
    /// Interaction logic for MainWindow.xaml
    /// </summary>
    public partial class MainWindow : Window
    {
        // TODO: 串口相关
        SerialPort mSerialPort = new SerialPort();
        private Thread recvThread;
        long recvTimems = 0;    // 用于计算串口接收完一帧数据
        int rxLen = 0;  // 串口接收到的数据长度
        byte[] rxBuff = new byte[128];  // 串口数据接收缓存
        private List<string> baudrateList = new List<string> {
            "4800",
            "9600",
            "19200",
            "38400",
            "57600",
            "115200",
            "256000",
            "1000000",
            "2000000",
            "3000000"
        };

        public MainWindow()
        {
            InitializeComponent();


            // 获取所有可用串口端口,并添加到comboBoxCOM
            string[] ports = System.IO.Ports.SerialPort.GetPortNames();
            comboBoxComName.ItemsSource = ports;
            comboBoxComName.SelectedIndex = 0;  // 默认选择索引
            comboBoxBaudrate.ItemsSource = baudrateList;    // 波特率设置combobox数据源
        }

        /// <summary>
        /// 窗口关闭处理
        /// </summary>
        /// <param name="e"></param>
        protected override void OnClosing(System.ComponentModel.CancelEventArgs e)
        {
            if (MessageBox.Show("确定要退出吗?", "确认", MessageBoxButton.YesNo) != MessageBoxResult.Yes)
            {
                // 用户选择“否”,取消关闭
                e.Cancel = true;
            }

            mSerialPort.Close();
            //mTimer.Dispose();

            if (recvThread != null)
            {                
                recvThread.Abort();
            }

            base.OnClosing(e);
        }


        private void recvTimerCalback(object obj)
        {
            this.Dispatcher.Invoke(new Action(() =>
            {
                // TODO: 处理接收到的数据

            }));
        }

        private void recvThreadTask()
        {
            Thread.Sleep(200);
            try
            {
                while (true)
                {
                    Thread.Sleep(1);

                    if (mSerialPort.IsOpen)
                    {
                        int datalength = mSerialPort.BytesToRead;
                        if (datalength >= 1)
                        {
                            //Console.WriteLine("BytesToRead:" + datalength);
                            for (int i = 0; i < datalength; i++)
                            {
                                recvTimems = Environment.TickCount; // 更新串口数据接收时间
                                byte data = (byte)mSerialPort.ReadByte();
                                rxBuff[rxLen++] = data;

                                if (rxBuff.Length == rxLen)
                                {
                                    rxLen = 0;
                                    Array.Clear(rxBuff, 0, rxBuff.Length);
                                    Console.WriteLine("Error================" + rxBuff.Length + "\n");
                                }

                                //Console.WriteLine(data.ToString("X2"));
                            }
                        }

                        recvTimerCalback(null);
                    }
                }

            }
            catch (Exception ex)
            {
                Console.WriteLine(" ----------异常------------");
            }
        }

        private void btnOpenCloseCom_Click(object sender, RoutedEventArgs e)
        {
            if (mSerialPort.IsOpen)
            {
                mSerialPort.Close();
                btnOpenCloseCom.Content = "打开串口";
                btnOpenCloseCom.Background = Brushes.Red;
                Console.WriteLine("关闭串口成功");
                Debug.WriteLine("关闭串口成功");
                comboBoxComName.IsEnabled = true;
                comboBoxBaudrate.IsEnabled = true;
                comboBoxDataBits.IsEnabled = true;
                comboBoxStopBits.IsEnabled = true;
                comboBoxParity.IsEnabled = true;
                comboBoxHandshake.IsEnabled = true;
            }
            else
            {
                // TODO: 串口默认设置
                mSerialPort.BaudRate = 4800; // 波特率
                mSerialPort.DataBits = 8;   // 数据位
                mSerialPort.StopBits = StopBits.One;    // 停止位
                mSerialPort.Parity = Parity.None;   // 校验位
                mSerialPort.Handshake = Handshake.None; // 流控位
                // mSerialPort.ReadTimeout = 1500; // 读超时
                // mSerialPort.Encoding = Encoding.UTF8; // 编码方式
                // mSerialPort.RtsEnable = true;
                // mSerialPort.DataReceived += SerialPort_DataReceived;

                Console.WriteLine("baudrate SelectedIndex:" + comboBoxBaudrate.SelectedIndex);
                Console.WriteLine("baudrate SelectedValue:" + comboBoxBaudrate.SelectedValue);
                Console.WriteLine("baudrate Text:" + comboBoxBaudrate.Text);

                // TODO: 串口端口选择
                mSerialPort.PortName = comboBoxComName.SelectedItem.ToString();

                // TODO: 设置串口波特率
                if (comboBoxBaudrate.SelectedIndex < 0)
                {
                    mSerialPort.BaudRate = Convert.ToInt32(comboBoxBaudrate.Text);
                }
                else
                {
                    switch (comboBoxBaudrate.SelectedValue)
                    {
                        case "4800":
                            mSerialPort.BaudRate = 4800;
                            break;
                        case "9600":
                            mSerialPort.BaudRate = 9600;
                            break;
                        case "19200":
                            mSerialPort.BaudRate = 19200;
                            break;
                        case "38400":
                            mSerialPort.BaudRate = 38400;
                            break;
                        case "57600":
                            mSerialPort.BaudRate = 57600;
                            break;
                        case "115200":
                            mSerialPort.BaudRate = 115200;
                            break;
                        case "256000":
                            mSerialPort.BaudRate = 256000;
                            break;
                        case "1000000":
                            mSerialPort.BaudRate = 1000000;
                            break;
                        case "2000000":
                            mSerialPort.BaudRate = 2000000;
                            break;
                        case "3000000":
                            mSerialPort.BaudRate = 3000000;
                            break;
                        default:
                            MessageBox.Show("波特率设置有误!");
                            break;
                    }
                }

                // TODO: 串口数据位设置
                switch (comboBoxDataBits.SelectedIndex)
                {
                    case 0:
                        mSerialPort.DataBits = 5;
                        break;
                    case 1:
                        mSerialPort.DataBits = 6;
                        break;
                    case 2:
                        mSerialPort.DataBits = 7;
                        break;
                    case 3:
                        mSerialPort.DataBits = 8;
                        break;
                    default:
                        mSerialPort.DataBits = 8;
                        break;
                }

                // TODO: 串口停止位设置
                switch (comboBoxStopBits.SelectedIndex)
                {
                    case 0:
                        mSerialPort.StopBits = StopBits.One;
                        break;
                    case 1:
                        mSerialPort.StopBits = StopBits.OnePointFive;
                        break;
                    case 2:
                        mSerialPort.StopBits = StopBits.Two;
                        break;
                    default:
                        mSerialPort.StopBits = StopBits.One;
                        break;
                }

                // TODO: 串口校验位设置
                switch (comboBoxParity.SelectedIndex)
                {
                    case 0:
                        mSerialPort.Parity = Parity.None;   // 无校验
                        Console.WriteLine("无校验");
                        break;
                    case 1:
                        mSerialPort.Parity = Parity.Odd;   // 奇校验
                        Console.WriteLine("奇校验");
                        break;
                    case 2:
                        mSerialPort.Parity = Parity.Even;   // 偶校验
                        Console.WriteLine("偶校验");
                        break;
                    case 3:
                        mSerialPort.Parity = Parity.Mark;   // 校验位1
                        Console.WriteLine("校验位1");
                        break;
                    case 4:
                        mSerialPort.Parity = Parity.Space;   // 校验位0
                        Console.WriteLine("校验位0");
                        break;
                    default:
                        mSerialPort.Parity = Parity.None;   // 无校验
                        break;
                }

                // TODO: 串口流控位设置
                switch (comboBoxHandshake.SelectedIndex)
                {
                    case 0:
                        mSerialPort.Handshake = Handshake.None;
                        break;
                    case 1:
                        mSerialPort.Handshake = Handshake.XOnXOff;                        
                        break;
                    case 2:
                        mSerialPort.Handshake = Handshake.RequestToSend;
                        break;
                    case 3:
                        mSerialPort.Handshake = Handshake.RequestToSendXOnXOff;
                        break;
                    default:
                        mSerialPort.Handshake = Handshake.None;
                        break;
                }

                // TODO: 尝试打开串口
                try 
                {
                    mSerialPort.Open();
                    btnOpenCloseCom.Content = "关闭串口";
                    btnOpenCloseCom.Background = Brushes.Green;
                }
                catch (Exception ex) 
                {
                    MessageBox.Show(ex.Message.ToString());
                }
            }
        }
    }
}
// TODO: 串口写入数据  3个参数(buf, offset, len);
mSerialPort.Write(new byte[] { 0xAA, 0x00, 0x08, 0x00, 0xB2, 0x55 }, 0, 6);

http://www.kler.cn/a/586894.html

相关文章:

  • 【fNIRS可视化学习1】基于NIRS-SPM进行光极可视化并计算通道坐标
  • 【Git学习笔记】Git结构原理及其分支管理模型分析
  • Ubuntu下管理多个GCC版本
  • 【数据分享】2000—2024年我国省市县三级逐月归一化植被指数(NDVI)数据(Shp/Excel格式)
  • 深入解析java Socket通信中的粘包与拆包问题及解决方案(中)
  • python 实现 A* 算法
  • 某大厂自动化工程师面试题
  • C语言每日一练——day_8
  • Qwen2.5的注意力秘籍:解锁高效模型的钥匙,分组查询注意力机制
  • .NET 9 中 OpenAPI 替代 Swagger 文档生成
  • apt-get update命令与apt update命令的区别
  • Assembly语言的安全开发
  • AI日报 - 2025年3月16日
  • 深入理解C/C++堆数据结构:从原理到实战
  • netsh实现TCP端口转发
  • 【Mapbox】介绍及基本使用
  • prompt提示词
  • 算法模型全解析:优缺点、场景适配与选择逻辑
  • 机器学习之特征工程
  • Go语言为什么运行比Java快