C#使用MQTT(二):MQTT客户端

上一篇我们初步设计了MQTT服务端

C#使用MQTT(一):MQTT服务端-CSDN博客

这里我们设计客户端MQTT Client,接上一篇

新建Windows窗体FormMqttClient

窗体FormMqttClient设计如图:

窗体FormMqttClient设计器相关代码如下

文件FormMqttClient.Designer.cs


namespace CultureDemo
{partial class FormMqttClient{/// <summary>/// Required designer variable./// </summary>private System.ComponentModel.IContainer components = null;/// <summary>/// Clean up any resources being used./// </summary>/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>protected override void Dispose(bool disposing){if (disposing && (components != null)){components.Dispose();}base.Dispose(disposing);}#region Windows Form Designer generated code/// <summary>/// Required method for Designer support - do not modify/// the contents of this method with the code editor./// </summary>private void InitializeComponent(){this.rtxtMessage = new System.Windows.Forms.RichTextBox();this.label8 = new System.Windows.Forms.Label();this.btnPublish = new System.Windows.Forms.Button();this.btnSubscribe = new System.Windows.Forms.Button();this.txtContent = new System.Windows.Forms.TextBox();this.label5 = new System.Windows.Forms.Label();this.txtTopicPublish = new System.Windows.Forms.TextBox();this.label6 = new System.Windows.Forms.Label();this.txtTopic = new System.Windows.Forms.TextBox();this.label7 = new System.Windows.Forms.Label();this.btnDisconnect = new System.Windows.Forms.Button();this.btnConnect = new System.Windows.Forms.Button();this.txtClientId = new System.Windows.Forms.TextBox();this.label4 = new System.Windows.Forms.Label();this.txtUpwd = new System.Windows.Forms.TextBox();this.label3 = new System.Windows.Forms.Label();this.txtUserName = new System.Windows.Forms.TextBox();this.label2 = new System.Windows.Forms.Label();this.txtPort = new System.Windows.Forms.TextBox();this.label1 = new System.Windows.Forms.Label();this.txtIP = new System.Windows.Forms.TextBox();this.lb = new System.Windows.Forms.Label();this.SuspendLayout();// // rtxtMessage// this.rtxtMessage.Location = new System.Drawing.Point(239, 37);this.rtxtMessage.Name = "rtxtMessage";this.rtxtMessage.Size = new System.Drawing.Size(623, 411);this.rtxtMessage.TabIndex = 51;this.rtxtMessage.Text = "";// // label8// this.label8.AutoSize = true;this.label8.Location = new System.Drawing.Point(242, 18);this.label8.Name = "label8";this.label8.Size = new System.Drawing.Size(29, 12);this.label8.TabIndex = 50;this.label8.Text = "消息";// // btnPublish// this.btnPublish.Location = new System.Drawing.Point(117, 425);this.btnPublish.Name = "btnPublish";this.btnPublish.Size = new System.Drawing.Size(75, 23);this.btnPublish.TabIndex = 49;this.btnPublish.Text = "发布";this.btnPublish.UseVisualStyleBackColor = true;this.btnPublish.Click += new System.EventHandler(this.btnPublish_Click);// // btnSubscribe// this.btnSubscribe.Location = new System.Drawing.Point(117, 286);this.btnSubscribe.Name = "btnSubscribe";this.btnSubscribe.Size = new System.Drawing.Size(75, 23);this.btnSubscribe.TabIndex = 48;this.btnSubscribe.Text = "订阅";this.btnSubscribe.UseVisualStyleBackColor = true;this.btnSubscribe.Click += new System.EventHandler(this.btnSubscribe_Click);// // txtContent// this.txtContent.Location = new System.Drawing.Point(92, 377);this.txtContent.Name = "txtContent";this.txtContent.Size = new System.Drawing.Size(100, 21);this.txtContent.TabIndex = 47;// // label5// this.label5.AutoSize = true;this.label5.Location = new System.Drawing.Point(45, 380);this.label5.Name = "label5";this.label5.Size = new System.Drawing.Size(29, 12);this.label5.TabIndex = 46;this.label5.Text = "内容";// // txtTopicPublish// this.txtTopicPublish.Location = new System.Drawing.Point(92, 341);this.txtTopicPublish.Name = "txtTopicPublish";this.txtTopicPublish.Size = new System.Drawing.Size(100, 21);this.txtTopicPublish.TabIndex = 45;// // label6// this.label6.AutoSize = true;this.label6.Location = new System.Drawing.Point(45, 344);this.label6.Name = "label6";this.label6.Size = new System.Drawing.Size(29, 12);this.label6.TabIndex = 44;this.label6.Text = "主题";// // txtTopic// this.txtTopic.Location = new System.Drawing.Point(92, 248);this.txtTopic.Name = "txtTopic";this.txtTopic.Size = new System.Drawing.Size(100, 21);this.txtTopic.TabIndex = 43;// // label7// this.label7.AutoSize = true;this.label7.Location = new System.Drawing.Point(45, 251);this.label7.Name = "label7";this.label7.Size = new System.Drawing.Size(29, 12);this.label7.TabIndex = 42;this.label7.Text = "主题";// // btnDisconnect// this.btnDisconnect.Location = new System.Drawing.Point(130, 205);this.btnDisconnect.Name = "btnDisconnect";this.btnDisconnect.Size = new System.Drawing.Size(75, 23);this.btnDisconnect.TabIndex = 41;this.btnDisconnect.Text = "断开";this.btnDisconnect.UseVisualStyleBackColor = true;this.btnDisconnect.Click += new System.EventHandler(this.btnDisconnect_Click);// // btnConnect// this.btnConnect.Location = new System.Drawing.Point(36, 205);this.btnConnect.Name = "btnConnect";this.btnConnect.Size = new System.Drawing.Size(75, 23);this.btnConnect.TabIndex = 40;this.btnConnect.Text = "连接";this.btnConnect.UseVisualStyleBackColor = true;this.btnConnect.Click += new System.EventHandler(this.btnConnect_Click);// // txtClientId// this.txtClientId.Location = new System.Drawing.Point(67, 164);this.txtClientId.Name = "txtClientId";this.txtClientId.Size = new System.Drawing.Size(134, 21);this.txtClientId.TabIndex = 39;this.txtClientId.Text = "snake";// // label4// this.label4.AutoSize = true;this.label4.Location = new System.Drawing.Point(20, 167);this.label4.Name = "label4";this.label4.Size = new System.Drawing.Size(41, 12);this.label4.TabIndex = 38;this.label4.Text = "客户ID";// // txtUpwd// this.txtUpwd.Location = new System.Drawing.Point(67, 127);this.txtUpwd.Name = "txtUpwd";this.txtUpwd.Size = new System.Drawing.Size(134, 21);this.txtUpwd.TabIndex = 37;this.txtUpwd.Text = "1";// // label3// this.label3.AutoSize = true;this.label3.Location = new System.Drawing.Point(32, 130);this.label3.Name = "label3";this.label3.Size = new System.Drawing.Size(29, 12);this.label3.TabIndex = 36;this.label3.Text = "密码";// // txtUserName// this.txtUserName.Location = new System.Drawing.Point(67, 100);this.txtUserName.Name = "txtUserName";this.txtUserName.Size = new System.Drawing.Size(134, 21);this.txtUserName.TabIndex = 35;this.txtUserName.Text = "a";// // label2// this.label2.AutoSize = true;this.label2.Location = new System.Drawing.Point(32, 103);this.label2.Name = "label2";this.label2.Size = new System.Drawing.Size(29, 12);this.label2.TabIndex = 34;this.label2.Text = "账号";// // txtPort// this.txtPort.Location = new System.Drawing.Point(67, 64);this.txtPort.Name = "txtPort";this.txtPort.Size = new System.Drawing.Size(134, 21);this.txtPort.TabIndex = 33;this.txtPort.Text = "12345";// // label1// this.label1.AutoSize = true;this.label1.Location = new System.Drawing.Point(32, 67);this.label1.Name = "label1";this.label1.Size = new System.Drawing.Size(29, 12);this.label1.TabIndex = 32;this.label1.Text = "端口";// // txtIP// this.txtIP.Location = new System.Drawing.Point(67, 22);this.txtIP.Name = "txtIP";this.txtIP.Size = new System.Drawing.Size(134, 21);this.txtIP.TabIndex = 31;this.txtIP.Text = "127.0.0.1";// // lb// this.lb.AutoSize = true;this.lb.Location = new System.Drawing.Point(20, 25);this.lb.Name = "lb";this.lb.Size = new System.Drawing.Size(41, 12);this.lb.TabIndex = 30;this.lb.Text = "IP地址";// // FormMqttClient// this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 12F);this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;this.ClientSize = new System.Drawing.Size(874, 525);this.Controls.Add(this.rtxtMessage);this.Controls.Add(this.label8);this.Controls.Add(this.btnPublish);this.Controls.Add(this.btnSubscribe);this.Controls.Add(this.txtContent);this.Controls.Add(this.label5);this.Controls.Add(this.txtTopicPublish);this.Controls.Add(this.label6);this.Controls.Add(this.txtTopic);this.Controls.Add(this.label7);this.Controls.Add(this.btnDisconnect);this.Controls.Add(this.btnConnect);this.Controls.Add(this.txtClientId);this.Controls.Add(this.label4);this.Controls.Add(this.txtUpwd);this.Controls.Add(this.label3);this.Controls.Add(this.txtUserName);this.Controls.Add(this.label2);this.Controls.Add(this.txtPort);this.Controls.Add(this.label1);this.Controls.Add(this.txtIP);this.Controls.Add(this.lb);this.Name = "FormMqttClient";this.Text = "FormMqttClient";this.Load += new System.EventHandler(this.FormMqttClient_Load);this.ResumeLayout(false);this.PerformLayout();}#endregionprivate System.Windows.Forms.RichTextBox rtxtMessage;private System.Windows.Forms.Label label8;private System.Windows.Forms.Button btnPublish;private System.Windows.Forms.Button btnSubscribe;private System.Windows.Forms.TextBox txtContent;private System.Windows.Forms.Label label5;private System.Windows.Forms.TextBox txtTopicPublish;private System.Windows.Forms.Label label6;private System.Windows.Forms.TextBox txtTopic;private System.Windows.Forms.Label label7;private System.Windows.Forms.Button btnDisconnect;private System.Windows.Forms.Button btnConnect;private System.Windows.Forms.TextBox txtClientId;private System.Windows.Forms.Label label4;private System.Windows.Forms.TextBox txtUpwd;private System.Windows.Forms.Label label3;private System.Windows.Forms.TextBox txtUserName;private System.Windows.Forms.Label label2;private System.Windows.Forms.TextBox txtPort;private System.Windows.Forms.Label label1;private System.Windows.Forms.TextBox txtIP;private System.Windows.Forms.Label lb;}
}

窗体FormMqttClient程序代码如下:客户端程序

文件FormMqttClient.cs

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using MQTTnet;
using MQTTnet.Client;namespace CultureDemo
{public partial class FormMqttClient : Form{IMqttClient mqttClient;public FormMqttClient(){InitializeComponent();rtxtMessage.ReadOnly = true;}/// <summary>/// 打印相关消息/// </summary>/// <param name="contents"></param>private void DisplayMessage(string contents){if (!this.IsHandleCreated){return;}this.BeginInvoke(new Action(() =>{if (rtxtMessage.TextLength >= 40960){rtxtMessage.Clear();}rtxtMessage.AppendText($"{DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss.fff")}->{contents}\n");rtxtMessage.ScrollToCaret();}));}private void FormMqttClient_Load(object sender, EventArgs e){mqttClient = new MqttFactory().CreateMqttClient();mqttClient.ConnectedAsync += MqttClient_ConnectedAsync;mqttClient.DisconnectedAsync += MqttClient_DisconnectedAsync;mqttClient.ApplicationMessageReceivedAsync += MqttClient_ApplicationMessageReceivedAsync;}private Task MqttClient_ApplicationMessageReceivedAsync(MqttApplicationMessageReceivedEventArgs e){return Task.Run(new Action(() =>{string msg = e.ApplicationMessage.ConvertPayloadToString();DisplayMessage($"接收消息:{msg}\nQoS={e.ApplicationMessage.QualityOfServiceLevel}\n客户端={e.ClientId}\n主题:{e.ApplicationMessage.Topic}");}));}private Task MqttClient_DisconnectedAsync(MqttClientDisconnectedEventArgs e){return Task.Run(new Action(async () =>{DisplayMessage($"已断开到MQTT服务端的连接.尝试重新连接");try{await Task.Delay(3000);//MqttClientOptions options = new MqttClientOptions();//await mqttClient.ConnectAsync(options);await mqttClient.ReconnectAsync();}catch (Exception ex){DisplayMessage($"重新连接服务器失败:{ex.Message}");}}));}private Task MqttClient_ConnectedAsync(MqttClientConnectedEventArgs e){return Task.Run(new Action(() =>{DisplayMessage($"连接到MQTT服务端成功.{e.ConnectResult.AssignedClientIdentifier}");}));}private async void btnConnect_Click(object sender, EventArgs e){try{MqttClientOptionsBuilder mqttClientOptionBuild = new MqttClientOptionsBuilder().WithClientId(this.txtClientId.Text).WithTcpServer(this.txtIP.Text, int.Parse(this.txtPort.Text)).WithCredentials(this.txtUserName.Text, this.txtUpwd.Text);MqttClientOptions options = mqttClientOptionBuild.Build();//开启await mqttClient.ConnectAsync(options);}catch (Exception ex) {DisplayMessage($"连接服务端时出现异常:{ex.Message}");}}private async void btnDisconnect_Click(object sender, EventArgs e){if (mqttClient != null){if (mqttClient.IsConnected){await mqttClient.DisconnectAsync();}mqttClient.Dispose();}}private async void btnSubscribe_Click(object sender, EventArgs e){if (string.IsNullOrWhiteSpace(this.txtTopic.Text)){DisplayMessage(">>> 请输入主题");return;}//在 MQTT 中有三种 QoS 级别: QuanlityOfService//At most once(0) 最多一次//At least once(1) 至少一次//Exactly once(2) 恰好一次MqttClientSubscribeOptionsBuilder subscribeOptionsBuilder = new MqttClientSubscribeOptionsBuilder();MqttClientSubscribeOptions subscribeOption = subscribeOptionsBuilder.WithTopicFilter(this.txtTopic.Text).Build();await mqttClient.SubscribeAsync(subscribeOption);DisplayMessage($">>> 成功订阅主题【{txtTopic.Text}】");}private async void btnPublish_Click(object sender, EventArgs e){if (string.IsNullOrWhiteSpace(this.txtTopicPublish.Text)){DisplayMessage(">>> 请输入主题");return;}MqttClientPublishResult result = await mqttClient.PublishStringAsync(this.txtTopicPublish.Text,this.txtContent.Text,MQTTnet.Protocol.MqttQualityOfServiceLevel.AtLeastOnce);//恰好一次, QoS 级别1   DisplayMessage($"发布消息--主题:{this.txtTopicPublish.Text},消息:{this.txtContent.Text},结果: {result.ReasonCode}");}}
}

为了一个应用程序可以作为客户端和服务端,我们在Program.cs增加切换开关

选择作为MQTT服务端和MQTT客户端

using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using System.Windows.Forms;namespace CultureDemo
{static class Program{/// <summary>/// 应用程序的主入口点。/// </summary>[STAThread]static void Main(){Application.EnableVisualStyles();Application.SetCompatibleTextRenderingDefault(false);DialogResult dialog = MessageBox.Show("请选择程序作为MQTT服务端还是客户端,选择\"是\"作为服务端,选择\"否\"作为客户端", "是否MQTT服务端", MessageBoxButtons.YesNo);if (dialog == DialogResult.Yes){Application.Run(new FormMqttServer());}else {Application.Run(new FormMqttClient());}}}
}

程序运行如图:

运行客户端与服务端通信

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/419404.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

uni-app--》打造个性化壁纸预览应用平台(四)完结篇

&#x1f3d9;️作者简介&#xff1a;大家好&#xff0c;我是亦世凡华、渴望知识储备自己的一名前端工程师 &#x1f304;个人主页&#xff1a;亦世凡华、 &#x1f306;系列专栏&#xff1a;uni-app &#x1f307;座右铭&#xff1a;人生亦可燃烧&#xff0c;亦可腐败&#xf…

论文写作神器!分享5款AI论文写作常用软件推荐

在当今学术研究和写作领域&#xff0c;AI论文写作工具的出现极大地提高了写作效率和质量。这些工具不仅能够帮助研究人员快速生成论文草稿&#xff0c;还能进行内容优化、查重和排版等操作。以下是五款目前最好用的AI论文写作软件推荐&#xff1a; 1. 千笔-AIPassPaper 千笔-…

SpringCache之本地缓存

针对不同的缓存技术&#xff0c;需要实现不同的cacheManager&#xff0c;Spring定义了如下的cacheManger实现。 CacheManger 描述 SimpleCacheManager 使用简单的Collection来存储缓存&#xff0c;主要用于测试 ConcurrentMapCacheManager 使用ConcurrentMap作为缓存技术&…

mac 安装redis

官网下载指定版本的redis https://redis.io/ 目前3.2.0 是最新最稳定的 版本 这里是历史版本下载 下载指定版本 安装 1.放到自定义目录下并解压 2.打开终端&#xff0c;执行命令 cd redis的安装目录下 make test -- 此命令的作用是将redis源代码编译成可执行文件&#xff0c…

java基础概念21-权限修饰符、代码块

一、权限修饰符 1-1、作用 权限修饰符&#xff0c;是用来控制一个成员能够被访问的范围的。 可以修饰&#xff1a;成员变量&#xff0c;方法&#xff0c;构造方法&#xff0c;内部类。 1-2、权限修饰符的分类 二、代码块 局部代码块构造代码块静态代码块 2-1、局部代码块 …

day1 QT

作业 #include "mywidget.h"MyWidget::MyWidget(QWidget *parent): QWidget(parent) {//设置窗口大小this->resize(1025,533);//固定窗口大小this->setFixedSize(1025,533);//设置窗口背景色,设置弧度//this->setStyleSheet("background-image:url(E:/…

肖扬老师好书《微权力下的项目管理(第3版)》读书笔记1

肖扬老师好书《微权力下的项目管理&#xff08;第3版&#xff09;》&#xff0c;的确不错&#xff0c;分别共读之。 第2章 精华 为了在项目过程中成为一名优秀的导演&#xff0c;项目经理要同时修炼领导和管理这两种不同的能 力&#xff0c;因为项目管理模式就是一种游走于领导…

计算机网络知识点复习——TCP协议的三次握手与四次挥手(连接与释放)

TCP协议的三次握手与四次挥手&#xff08;连接与释放&#xff09; 一、前言二、简单的知识准备1. TCP协议的主要特点2. TCP报文段 三、TCP连接的建立&#xff08;三次握手&#xff09;四、TCP连接的释放&#xff08;四次挥手&#xff09;五、TCP连接与释放的总结六、结束语 一、…

MySQL record 01 part

更改密码&#xff1a; alter user rootlocalhost identified with mysql_native_password by ‘123456’; 注意&#xff1a; 在命令行方式下&#xff0c;每条MySQL的命令都是以分号结尾的&#xff0c;如果不加分号&#xff0c;MySQL会继续等待用户输入命令&#xff0c;直到MyS…

vue2-elementUI-初始化启动项目-git

前置基础 资料下载-阿里云盘 vueaxioselement-uinpmvscode 初始化项目 1.创建vue2工程 1.1 vue create projectName1.2 选择 1.3 初始化 vue-cli 的核心步骤&#xff1a; Manually select features (*) Babel ( ) TypeScript ( ) Progressive Web App (PWA) Support …

【深度学习讲解笔记】前言

小编为AI专业的本科学生&#xff0c;最近入手了一本《深度学习讲解》的书&#xff0c;由于封面画了苹果&#x1f34e;&#xff0c;所以也叫苹果书&#xff0c;这本书目前在全网的热度很高。 本书是根据李宏毅老师讲授的《机器学习》课程编写的&#xff0c;作者是来自DataWhale…

Python QT实现A-star寻路算法

目录 1、界面使用方法 2、注意事项 3、补充说明 用Qt5搭建一个图形化测试寻路算法的测试环境。 1、界面使用方法 设定起点&#xff1a; 鼠标左键双击&#xff0c;设定红色的起点。左键双击设定起点&#xff0c;用红色标记。 设定终点&#xff1a; 鼠标右键双击&#xf…

Uniapp基于uni拦截器+Promise的请求函数封装

最近在学Uniapp&#xff0c;到封装请求的时候本来还想用axios&#xff0c;但是看到一些教学视频有更简单的方法&#xff0c; 基于uni的拦截器和Promise封装的请求函数 但是他们是用TS写的&#xff0c;还没学到TS&#xff0c;我就把JS写了&#xff0c;最终也是请求成功 // src/…

电动机制造5G智能工厂工业物联数字孪生平台,推进制造业数字化转型

电动机制造5G智能工厂工业物联数字孪生平台&#xff0c;推进制造业数字化转型。5G智能工厂与物联数字孪生平台的融合应用&#xff0c;为电动机制造业的数字化转型铺设了一条高速通道。这一创新模式不仅极大地提升了生产效率&#xff0c;还深刻改变了产品的设计、生产、管理及运…

EasyExcel模板导出与公式计算(下)

目录 环境要求 功能预览 需求分析 导入依赖 制作模板 编写代码 格式优化 最终效果 总结 在上一篇 EasyExcel模板导出与公式计算&#xff08;上&#xff09;-CSDN博客 文章中我们知道了在若依中使用自带的Excel注解来实现表格数据的导出&#xff0c;并且通过重写相关接…

【Python 千题 —— 算法篇】无重复字符最长子段

Python 千题持续更新中 …… 脑图地址 &#x1f449;&#xff1a;⭐https://twilight-fanyi.gitee.io/mind-map/Python千题.html⭐ 题目背景 在编程过程中&#xff0c;处理字符串的任务时常遇到&#xff0c;其中一个经典问题是查找无重复字符的最长子串。这在很多应用场景中…

redisson中的分布式锁

我的博客大纲 我的后端学习大纲 a.redisson概述&#xff1a; 1.Redisson是一个在Redis的基础上实现的Java驻内存数据网格&#xff08;In-Memory Data Grid&#xff09;2.redisson介绍官方文档地址&#xff1a;3.Redisson它不仅提供了一系列的分布式的Java常用对象&#xff0c;还…

使用vscode编辑matlab完美解决方法

vscode里面的matlab插件都不好用&#xff0c;需要搭配互补一下 1先安装MATLAB 这个插件可以进行代码高亮、格式化、跳转&#xff0c;F5运行所有代码&#xff0c;或者选中要运行的代码&#xff0c;右键单独运行&#xff0c; 优点&#xff1a;运行速度很快&#xff0c;和matlab里…

vcruntime140.dll丢失报错处理及dll下载修复方法

概述 vcruntime140.dll是Visual C Redistributable for Visual Studio的一个动态链接库文件。 如果你在运行某个程序时遇到了vcruntime140.dll丢失的错误&#xff0c;你可以尝试以下解决方法&#xff1a; 重新安装程序&#xff1a; 如果你只在运行某个特定程序时出现了该错误…

云手机怎样简化海外社媒平台运营

随着越来越多的卖家希望拓展海外市场&#xff0c;运营TikTok、Facebook等社交媒体平台已经成为吸引流量和促进销售的重要手段。然而&#xff0c;在管理海外社媒账号的过程中&#xff0c;许多人会面临网络连接的问题。这时&#xff0c;使用一款高效便捷的云手机工具就显得尤为便…