229 lines
8.6 KiB
C#
229 lines
8.6 KiB
C#
using System.Text;
|
|
using System.Windows;
|
|
using System.Windows.Controls;
|
|
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;
|
|
using System.Net.Sockets;//socket库
|
|
using System.Net.Http;
|
|
using System.Net;
|
|
using System.IO;
|
|
using System;
|
|
using System.Security.Policy;
|
|
using log4net;
|
|
using log4net.Config;
|
|
using System.Text.Json;
|
|
using chatclient.Data;
|
|
using System.ComponentModel;
|
|
using System.Collections.ObjectModel;
|
|
using System.Windows.Threading;
|
|
using System.Collections.Specialized;
|
|
|
|
[assembly: XmlConfigurator(ConfigFile = "config/log4net.config", Watch = true)]
|
|
namespace chatclient
|
|
{
|
|
/// <summary>
|
|
/// Interaction logic for MainWindow.xaml
|
|
/// </summary>
|
|
public partial class MainWindow : Window, INotifyPropertyChanged
|
|
{
|
|
LoginWindow Login = new();
|
|
static string? receive;
|
|
public static string? UserName = null;
|
|
private static readonly ILog log = LogManager.GetLogger(typeof(MainWindow));
|
|
public static Socket? Client;
|
|
public static readonly HttpClient HttpClient = new HttpClient();
|
|
public event PropertyChangedEventHandler? PropertyChanged;
|
|
private string? _Username;
|
|
public string? Username
|
|
{
|
|
get { return _Username; }
|
|
set
|
|
{
|
|
_Username = value;
|
|
Update("Username");
|
|
}
|
|
}
|
|
// 消息列表
|
|
public ObservableCollection<ChatMessage> Messages { get; } = new ObservableCollection<ChatMessage>();
|
|
private ItemsControl MessageList => messageList;
|
|
private ScrollViewer MessageScroller => messageScroller;
|
|
private void Update(string UpdateName)
|
|
{
|
|
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(UpdateName));
|
|
}
|
|
public MainWindow()
|
|
{
|
|
InitializeComponent();
|
|
this.DataContext = this;
|
|
log.Info("Hello World!");
|
|
this.Hide();
|
|
Client = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
|
|
try
|
|
{
|
|
log.Info($"连接服务器 {Server.ServerIP}:{Server.ServerPort} ");
|
|
Client.Connect(Server.ServerIP, Server.ServerPort);
|
|
}
|
|
catch (Exception ex)
|
|
{
|
|
Client.Close();
|
|
log.Error(ex);
|
|
}
|
|
Login.Show();
|
|
Thread th = new Thread(Receive);
|
|
th.Start();
|
|
MessageList.ItemsSource = Messages;
|
|
((INotifyCollectionChanged)MessageList.Items).CollectionChanged += (s, e) =>
|
|
{
|
|
// 确保有足够的时间让UI更新
|
|
Dispatcher.BeginInvoke(new Action(() =>
|
|
{
|
|
MessageScroller.ScrollToEnd();
|
|
}), DispatcherPriority.ContextIdle);
|
|
};
|
|
}
|
|
static void Receive()
|
|
{
|
|
byte[] buffer = new byte[1024];
|
|
try
|
|
{
|
|
while (true)
|
|
{
|
|
int num = Client!.Receive(buffer);
|
|
if (num == 0) break;
|
|
if (Client.Poll(100, SelectMode.SelectRead) && Client.Available == 0 || !Client.Connected)
|
|
{
|
|
log.Error("连接已断开");
|
|
break;
|
|
}
|
|
receive = Encoding.UTF8.GetString(buffer, 0, num);
|
|
response(receive);
|
|
}
|
|
}
|
|
catch (Exception ex)
|
|
{
|
|
log.Error(ex);
|
|
}
|
|
finally
|
|
{
|
|
Client?.Close();
|
|
}
|
|
}
|
|
|
|
static void response(string msg)
|
|
{
|
|
log.Info($"收到服务器消息: {msg}");
|
|
try
|
|
{
|
|
var Type = JsonSerializer.Deserialize<RegisterData>(msg);
|
|
if (Type != null)
|
|
{
|
|
var LoginResponse = JsonSerializer.Deserialize<LoginResultData>(msg);
|
|
if (Type.type == "login_1")
|
|
{
|
|
if (LoginResponse!.status == "success" && LoginResponse != null)
|
|
{
|
|
log.Info($"用户 {UserName} 登录成功");
|
|
Application.Current.Dispatcher.Invoke(() =>
|
|
{
|
|
var mainWindow = Application.Current.Windows.OfType<MainWindow>().FirstOrDefault();
|
|
if (mainWindow != null)
|
|
{
|
|
mainWindow.Username = UserName;
|
|
mainWindow.Show();
|
|
var loginWindow = Application.Current.Windows.OfType<LoginWindow>().FirstOrDefault();
|
|
loginWindow?.Close();
|
|
mainWindow.Activate();
|
|
}
|
|
});
|
|
}
|
|
else
|
|
{
|
|
Application.Current.Dispatcher.Invoke(() =>
|
|
{
|
|
var loginWindow = Application.Current.Windows.OfType<LoginWindow>().FirstOrDefault();
|
|
if (loginWindow != null)
|
|
{
|
|
loginWindow.LoginMsg = LoginResponse != null ? LoginResponse.message : "服务器返回错误";
|
|
}
|
|
});
|
|
}
|
|
}
|
|
else if(Type.type == "login_0" && LoginResponse != null)
|
|
{
|
|
log.Warn($"登录失败: {LoginResponse.message}\nMsg:{msg}");
|
|
Application.Current.Dispatcher.Invoke(() =>
|
|
{
|
|
var loginWindow = Application.Current.Windows.OfType<LoginWindow>().FirstOrDefault();
|
|
if (loginWindow != null)
|
|
{
|
|
loginWindow.LoginMsg = LoginResponse.message;
|
|
}
|
|
});
|
|
}
|
|
else
|
|
{
|
|
Application.Current.Dispatcher.Invoke(() =>
|
|
{
|
|
var loginWindow = Application.Current.Windows.OfType<LoginWindow>().FirstOrDefault();
|
|
if (loginWindow != null)
|
|
{
|
|
loginWindow.LoginMsg = LoginResponse != null ? LoginResponse.message : "服务器返回错误";
|
|
}
|
|
});
|
|
}
|
|
}
|
|
}
|
|
catch (JsonException ex)
|
|
{
|
|
log.Error("JSON解析错误", ex);
|
|
}
|
|
catch (Exception ex)
|
|
{
|
|
log.Error("处理响应时发生错误", ex);
|
|
}
|
|
}
|
|
private void SendMessage_Click(object sender, RoutedEventArgs e)
|
|
{
|
|
SendMessage();
|
|
}
|
|
private void SendMessage()
|
|
{
|
|
if (string.IsNullOrWhiteSpace(txtMessage.Text))
|
|
return;
|
|
|
|
// 获取当前选中的联系人
|
|
//var contact = cmbContacts.SelectedItem as Contact;
|
|
// 判断是否为群组,若是则收件人设为“所有人”,否则为联系人显示名
|
|
//string recipient = contact?.IsGroup == true ? "所有人" : contact?.DisplayName;
|
|
|
|
// 创建新消息
|
|
var newMessage = new ChatMessage
|
|
{
|
|
Sender = "我",
|
|
Type = MessageType.Text,
|
|
Image = new BitmapImage(new Uri("pack://application:,,,/user.png", UriKind.Absolute)), // 默认头像
|
|
Content = txtMessage.Text,
|
|
Timestamp = DateTime.Now,
|
|
Alignment = HorizontalAlignment.Right, // 自己发送的消息靠右
|
|
SenderColor = new SolidColorBrush(Colors.Blue)
|
|
};
|
|
// 添加到消息列表
|
|
Messages.Add(newMessage);
|
|
// 清空输入框
|
|
txtMessage.Clear();
|
|
}
|
|
// 消息输入框回车事件
|
|
private void MessageInput_KeyDown(object sender, KeyEventArgs e)
|
|
{
|
|
if (e.Key == Key.Enter && Keyboard.Modifiers != ModifierKeys.Shift)
|
|
{
|
|
SendMessage();
|
|
e.Handled = true; // 阻止换行
|
|
}
|
|
}
|
|
}
|
|
} |