国产 无码 综合区,色欲AV无码国产永久播放,无码天堂亚洲国产AV,国产日韩欧美女同一区二区

基于.net6的WPF程序使用SignalR進行通信

這篇具有很好參考價值的文章主要介紹了基于.net6的WPF程序使用SignalR進行通信。希望對大家有所幫助。如果存在錯誤或未考慮完全的地方,請大家不吝賜教,您也可以點擊"舉報違法"按鈕提交疑問。

之前寫的SignalR通信,是基于.net6api,BS和CS進行通信的。

.net6API使用SignalR+vue3聊天+WPF聊天_signalr wpf_故里2130的博客-CSDN博客

今天寫一篇關(guān)于CS客戶端的SignalR通信,后臺服務(wù)使用.net6api?。其實和之前寫的差不多,主要在于服務(wù)端以后臺進程的方式存在,而客戶端以exe方式存在,其實代碼都一樣,只是生成的方式不一樣。

?一、服務(wù)端

1.首先建立一個.net6的webapi服務(wù)端

基于.net6的WPF程序使用SignalR進行通信,C#,.net,wpf

2.Program.cs

using SignalRServerApi.Controllers;

namespace SignalRServerApi
{
    public class Program
    {
        public static void Main(string[] args)
        {
            var builder = WebApplication.CreateBuilder(args);

            // Add services to the container.

            builder.Services.AddControllers();
            // Learn more about configuring Swagger/OpenAPI at https://aka.ms/aspnetcore/swashbuckle
            builder.Services.AddEndpointsApiExplorer();
            builder.Services.AddSwaggerGen();
            builder.Services.AddSignalR();   //增加AddSignalR
            string[] urls = new[] { "http://localhost:3000" };       //此處一定要寫指定的ip地址,地址是前端的ip地址,坑了我1天的時間
            builder.Services.AddCors(options =>
                options.AddDefaultPolicy(builder => builder.WithOrigins(urls)
                    .AllowAnyMethod().AllowAnyHeader().AllowCredentials())
            );
            var app = builder.Build();

            // Configure the HTTP request pipeline.
            if (app.Environment.IsDevelopment())
            {
                app.UseSwagger();
                app.UseSwaggerUI();
            }
            app.UseCors(); //增加跨域問題
            app.UseHttpsRedirection();

            app.UseAuthorization();


            app.MapControllers();
            app.MapHub<ChatHub>("/api/chat");  //前端訪問的地址,2邊要統(tǒng)一就行了
            app.Run();
        }
    }
}

3.ChatHub.cs

using Microsoft.AspNetCore.SignalR;
using System.Collections.Concurrent;

namespace SignalRServerApi.Controllers
{
    public class ChatHub : Hub
    {
        private static Dictionary<string, string> dicUsers = new Dictionary<string, string>();
        public override Task OnConnectedAsync()    //登錄
        {
            Console.WriteLine($"ID:{Context.ConnectionId} 已連接");   //控制臺記錄
            var cid = Context.ConnectionId;
            //根據(jù)id獲取指定客戶端
            var client = Clients.Client(cid);

            //向指定用戶發(fā)送消息
            //client.SendAsync("Self", cid);

            //像所有用戶發(fā)送消息
            Clients.All.SendAsync("ReceivePublicMessageLogin", $"{cid}加入了聊天室");        //界面顯示登錄
            return base.OnConnectedAsync();
        }
        public override Task OnDisconnectedAsync(Exception? exception)       //退出的時候
        {
            Console.WriteLine($"ID:{Context.ConnectionId} 已斷開");
            var cid = Context.ConnectionId;
            //根據(jù)id獲取指定客戶端
            var client = Clients.Client(cid);

            //向指定用戶發(fā)送消息
            //client.SendAsync("Self", cid);

            //像所有用戶發(fā)送消息
            Clients.All.SendAsync("ReceivePublicMessageLogin", $"{cid}離開了聊天室");        //界面顯示登錄
            return base.OnDisconnectedAsync(exception);
        }
        /// <summary>
        /// 向所有客戶端發(fā)送消息
        /// </summary>
        /// <param name="user"></param>
        /// <param name="message"></param>
        /// <returns></returns>
        public async Task SendPublicMessage(string user, string message)
        {                                                     //string user,
            await Clients.All.SendAsync("ReceivePublicMessage", user, message);   //ReceiveMessage 提供給客戶端使用
        }

        /// <summary>
        /// 用戶登錄,密碼就不判斷了
        /// </summary>
        /// <param name="userId"></param>
        public void Login(string userId)     //對應(yīng)前端的invoke
        {
            if (!dicUsers.ContainsKey(userId))
            {
                dicUsers[userId] = Context.ConnectionId;
            }
            Console.WriteLine($"{userId}登錄成功,ConnectionId={Context.ConnectionId}");
            //向所有用戶發(fā)送當(dāng)前在線的用戶列表
            Clients.All.SendAsync("dicUsers", dicUsers.Keys.ToList());   //對應(yīng)前端的on
        }

        public void ChatOne(string userId, string toUserId, string msg)     //用戶  發(fā)送到的用戶      發(fā)送的消息
        {
            string newMsg = $"{userId}對你說{msg}";//組裝后的消息體
            //如果當(dāng)前用戶在線
            if (dicUsers.ContainsKey(toUserId))
            {
                Clients.Client(dicUsers[toUserId]).SendAsync("ChatInfo", newMsg);
            }
            else
            {
                //如果當(dāng)前用戶不在線,正常是保存數(shù)據(jù)庫,等上線時加載,暫時不做處理
            }
        }

    }

}

4.生成方式

選擇Windows應(yīng)用程序?

基于.net6的WPF程序使用SignalR進行通信,C#,.net,wpf

5.運行

運行后,服務(wù)是以進程的方式存在

基于.net6的WPF程序使用SignalR進行通信,C#,.net,wpf

6.效果

此時需要注意代碼的這個地址

基于.net6的WPF程序使用SignalR進行通信,C#,.net,wpf

基于.net6的WPF程序使用SignalR進行通信,C#,.net,wpf

當(dāng)然IP和端口都可以修改的,也可以增加網(wǎng)頁顯示,根據(jù)業(yè)務(wù)而定。?

二、客戶端

1.首先建立一個.net6的wpf客戶端

基于.net6的WPF程序使用SignalR進行通信,C#,.net,wpf

2.安裝Microsoft.AspNetCore.SignalR.Client

基于.net6的WPF程序使用SignalR進行通信,C#,.net,wpf

3.建立界面

界面代碼

<Window x:Class="SignalRClient.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:local="clr-namespace:SignalRClient"
        mc:Ignorable="d"
        Title="MainWindow" Height="450" Width="800">
    <Grid>
        <StackPanel Orientation="Vertical">
            <StackPanel Orientation="Horizontal">
                <TextBlock>賬號:</TextBlock>
                <TextBox Name="user" Width="300" Height="20" Margin="0,5"></TextBox>
            </StackPanel>
            <StackPanel Orientation="Horizontal">
                <TextBlock>密碼:</TextBlock>
                <TextBox Name="password" Width="300" Height="20" Margin="0,5"></TextBox>
            </StackPanel>
            <StackPanel Orientation="Horizontal"  >
                <Button Name="btnLogin" Width="50" Height="20" Margin="0,5" Click="btnLogin_Click">登錄</Button>
            </StackPanel>
            <StackPanel Orientation="Horizontal">
                <TextBlock>發(fā)送給某人:</TextBlock>
                <TextBox Name="toUser" Width="300" Height="20" Margin="0,5" ></TextBox>
            </StackPanel>
            <StackPanel Orientation="Horizontal">
                <TextBlock>發(fā)送內(nèi)容:</TextBlock>
                <TextBox Name="content" Width="300" Height="20" Margin="0,5"></TextBox>
            </StackPanel>
            <StackPanel Orientation="Horizontal">
                <Button Name="btnSendAll" Width="100" Height="20" Margin="0,5" Click="btnSendAll_Click">發(fā)送所有人</Button>
                <Button Name="btnSendOne" Width="100" Height="20" Margin="0,5" Click="btnSendOne_Click">發(fā)送到個人</Button>
            </StackPanel>
            <RichTextBox Height="100" Name="rtbtxt">
                <FlowDocument>
                    <Paragraph>
                        <Run Text=""/>
                    </Paragraph>
                </FlowDocument>
            </RichTextBox>
        </StackPanel>
    </Grid>
</Window>

4.后臺代碼

using Microsoft.AspNetCore.SignalR.Client;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Net.Http;
using System.Net.Security;
using System.Security.Cryptography.X509Certificates;
using System.Text;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;

namespace SignalRClient
{
    /// <summary>
    /// Interaction logic for MainWindow.xaml
    /// </summary>
    public partial class MainWindow : Window
    {
        private HubConnection hubConnection;
        public MainWindow()
        {
            InitializeComponent();
            //rtbtxt.AppendText("4444");
        }

        private void btnLogin_Click(object sender, RoutedEventArgs e)
        {
            //此處和VUE3界面是一樣的,參照寫就行了。
            //1.初始化
            InitInfo();
            //2.連接
            Link();
            //3.監(jiān)聽
            Listen();
            //4.登錄
            Login();


        }
        /// <summary>
        /// 初始化
        /// </summary>
        private void InitInfo()
        {
            hubConnection = new HubConnectionBuilder().WithUrl("http://127.0.0.1:5000/api/chat", (opt) =>
            {
                opt.HttpMessageHandlerFactory = (message) =>
                {
                    if (message is HttpClientHandler clientHandler)
                        // bypass SSL certificate
                        clientHandler.ServerCertificateCustomValidationCallback +=
                            (sender, certificate, chain, sslPolicyErrors) => { return true; };
                    return message;
                };

            }).WithAutomaticReconnect().Build();
            hubConnection.KeepAliveInterval = TimeSpan.FromSeconds(5);
        }
        List<string> LoginUser;
        string msgContent;

        /// <summary>
        /// 監(jiān)聽數(shù)據(jù)的變化
        /// </summary>
        private void Listen()
        {
            hubConnection.On<List<string>>("dicUsers", msg =>
            {
                LoginUser = msg;
                string s = string.Empty;
                foreach (string item in msg)
                {
                    s += item + "用戶登錄" + Environment.NewLine;
                }
                rtbtxt.AppendText(s);


            });  //匿名方法  真實環(huán)境中,此處使用的是屬性變化,不要使用賦值的方式
            hubConnection.On<string>("ReceivePublicMessageLogin", msg => { msgContent = msg; rtbtxt.AppendText(msg + Environment.NewLine); });
            hubConnection.On<string, string>("ReceivePublicMessage", (user, msg) => { msgContent = msg; rtbtxt.AppendText(user + "說:" + msg + Environment.NewLine); });  //匿名方法
            hubConnection.On<string>("ChatInfo", msg => { msgContent = msg; rtbtxt.AppendText(msg + Environment.NewLine); });
        }

        /// <summary>
        /// 連接
        /// </summary>
        private async void Link()
        {
            try
            {
                await hubConnection.StartAsync();
            }
            catch (Exception ex)
            {
                MessageBox.Show(ex.Message);
            }
        }
        private static bool ValidateCertificate(object sender, X509Certificate certificate, X509Chain chain, SslPolicyErrors sslPolicyErrors)
        {
            // 在這里添加你的證書驗證邏輯
            // 返回true表示驗證通過,返回false表示驗證失敗
            // 例如,你可以添加自定義的證書驗證邏輯來允許不受信任的證書
            return true;
        }

        private void Login()
        {
            hubConnection.InvokeAsync("Login", user.Text);
        }
        private void btnSendAll_Click(object sender, RoutedEventArgs e)
        {
            hubConnection.InvokeAsync("SendPublicMessage", user.Text, content.Text);
        }

        private void btnSendOne_Click(object sender, RoutedEventArgs e)
        {
            hubConnection.InvokeAsync("ChatOne", user.Text, toUser.Text, content.Text);
        }

    }
}

這里需要注意, 一起運行不會報錯,但是單獨運行會報錯

The SSL connection could not be established, see inner exception

需要在初始化InitInfo()方法中增加HttpMessageHandlerFactory,即可解決。

?5.效果

基于.net6的WPF程序使用SignalR進行通信,C#,.net,wpf

此時,后臺的服務(wù)以進行的方式存在,然后可以和客戶端進行通信,其實和之前寫的是一樣的,只是生成方式不同而已。?

?源碼

https://download.csdn.net/download/u012563853/88061397

來源:基于.net6的WPF程序使用SignalR進行通信-CSDN博客文章來源地址http://www.zghlxwxcb.cn/news/detail-586906.html

到了這里,關(guān)于基于.net6的WPF程序使用SignalR進行通信的文章就介紹完了。如果您還想了解更多內(nèi)容,請在右上角搜索TOY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!

本文來自互聯(lián)網(wǎng)用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務(wù),不擁有所有權(quán),不承擔(dān)相關(guān)法律責(zé)任。如若轉(zhuǎn)載,請注明出處: 如若內(nèi)容造成侵權(quán)/違法違規(guī)/事實不符,請點擊違法舉報進行投訴反饋,一經(jīng)查實,立即刪除!

領(lǐng)支付寶紅包贊助服務(wù)器費用

相關(guān)文章

  • 【.NET6+WPF】WPF使用prism框架+Unity IOC容器實現(xiàn)MVVM雙向綁定和依賴注入

    【.NET6+WPF】WPF使用prism框架+Unity IOC容器實現(xiàn)MVVM雙向綁定和依賴注入

    前言:在C/S架構(gòu)上,WPF無疑已經(jīng)是“桌面一霸”了。在.NET生態(tài)環(huán)境中,很多小伙伴還在使用Winform開發(fā)C/S架構(gòu)的桌面應(yīng)用。但是WPF也有很多年的歷史了,并且基于MVVM的開發(fā)模式,受到了很多開發(fā)者的喜愛。 并且隨著工業(yè)化的進展,以及幾年前微軟對.NET平臺的開源,國內(nèi)大多

    2024年02月06日
    瀏覽(28)
  • WPF+ASP.NET SignalR實現(xiàn)簡易在線聊天功能

    WPF+ASP.NET SignalR實現(xiàn)簡易在線聊天功能

    在實際業(yè)務(wù)中,當(dāng)后臺數(shù)據(jù)發(fā)生變化,客戶端能夠?qū)崟r的收到通知,而不是由用戶主動的進行頁面刷新才能查看,這將是一個非常人性化的設(shè)計。有沒有那么一種場景,后臺數(shù)據(jù)明明已經(jīng)發(fā)生變化了,前臺卻因為沒有及時刷新,而導(dǎo)致頁面顯示的數(shù)據(jù)與實際存在差異,從而造

    2024年02月07日
    瀏覽(19)
  • WPF:.Net6框架下,使用Material Design過程中,配色和UI字體模糊的問題

    WPF:.Net6框架下,使用Material Design過程中,配色和UI字體模糊的問題

    有關(guān)Material Design的使用方法,請自行參考這個鏈接 WPF使用Material Design 下面,直接上我碰到的問題及解決方式 默認(rèn)情況下,Material Design是提供了很多主題配色,但難免有些太過“出挑”,不適合工控軟件的風(fēng)格。 所以,下面簡單介紹一下手動配色的基礎(chǔ)方法: 代表采用的是

    2024年02月06日
    瀏覽(35)
  • WPF .Net6框架下, 使用 Microsoft.Xaml.Behaviors.Wpf 的Interaction.Triggers特性,實現(xiàn)ComboBox 在展開時,觸發(fā)刷新列表內(nèi)容的動作

    ComboBox 在WPF中是常見的控件。 一般情況下,在綁定好數(shù)據(jù)源后,其內(nèi)容是固定的。 當(dāng)然,你也可以實時刷新,但這將帶來較高的資源消耗。 因此有個折中的辦法: 只在它在展開時,自動更新列表內(nèi)容。 當(dāng)前文章基于 .Net6框架,其他框架不適用。 這個是用于平替winform某個組

    2024年02月09日
    瀏覽(23)
  • .net6下[WPF+yolov5+opencvsharp]

    .net6下[WPF+yolov5+opencvsharp]

    1. 簡介 機緣巧合下寫的一個工程,本來是作為商家視覺識別上位機的替代品,但是最后沒用上,因此只開發(fā)了一半(廠家升級了攝像頭和軟件) 該工程基于WPF的.net6+mvvm 調(diào)用攝像頭進行識別 opencv開攝像頭(不想自己封裝win32api),yolov5對圖像進行檢測 2.引用庫 MVVM CommunityToolkit.Mv

    2024年02月08日
    瀏覽(19)
  • .Net6使用WebSocket與前端進行通信

    .Net6使用WebSocket與前端進行通信

    1. 創(chuàng)建類WebSocketTest: 2. 在program.cs中進行綁定 3. 使用websocket在線工具模擬請求:

    2024年02月03日
    瀏覽(32)
  • 微信小程序如何使用原生Websocket與Asp.Net Core SignalR 通信

    微信小程序如何使用原生Websocket與Asp.Net Core SignalR 通信

    如題,這可能算是.net 做小程序的服務(wù)端時,繞不開的一個問題,老生常談了。同樣的問題,我記得我2018/19年的一個項目的解決方案是: 修改官方的SignalR.js的客戶端 :把里面用到瀏覽器的Websocket改成微信小程序的官方api的。目前網(wǎng)上也有不少這樣的方案,已經(jīng)改好開源了;

    2024年02月08日
    瀏覽(129)
  • 微信小程序如何使用原生Websocket api與Asp.Net Core SignalR 通信

    微信小程序如何使用原生Websocket api與Asp.Net Core SignalR 通信

    如題,這可能算是.net 做小程序的服務(wù)端時,繞不開的一個問題,老生常談了。同樣的問題,我記得我2018/19年的一個項目的解決方案是: 修改官方的SignalR.js的客戶端 :把里面用到瀏覽器的Websocket改成微信小程序的官方api的。目前網(wǎng)上也有不少這樣的方案,已經(jīng)改好開源了;

    2024年02月09日
    瀏覽(39)
  • .NET6 項目使用RabbitMQ實現(xiàn)基于事件總線EventBus通信

    .NET6 項目使用RabbitMQ實現(xiàn)基于事件總線EventBus通信

    一、概念及介紹 ????????通常通過使用事件總線實現(xiàn)來執(zhí)行此發(fā)布/訂閱系統(tǒng)。 事件總線可以設(shè)計為包含 API 的接口,該 API 是訂閱和取消訂閱事件和發(fā)布事件所需的。 它還可以包含一個或多個基于跨進程或消息通信的實現(xiàn),例如支持異步通信和發(fā)布/訂閱模型的消息隊列或

    2024年04月28日
    瀏覽(26)
  • 使用Autofac進行服務(wù)注冊,適用版本.Net6(程序集、泛型)

    具體的也可以去參考官網(wǎng):https://autofac.readthedocs.io/en/latest/integration/aspnetcore.html 首先在Program.cs所屬的層中引用nuget包: nuget網(wǎng)址:https://www.nuget.org/packages? 可以使用NuGet包管理器進行搜索安裝 在Program.cs中加入如下代碼: 代碼中SmartHealthcare.Application可以替換為具體自己項目中Ap

    2024年02月16日
    瀏覽(24)

覺得文章有用就打賞一下文章作者

支付寶掃一掃打賞

博客贊助

微信掃一掃打賞

請作者喝杯咖啡吧~博客贊助

支付寶掃一掃領(lǐng)取紅包,優(yōu)惠每天領(lǐng)

二維碼1

領(lǐng)取紅包

二維碼2

領(lǐng)紅包