You cannot select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
113 lines
2.7 KiB
C#
113 lines
2.7 KiB
C#
using System;
|
|
using System.Collections.ObjectModel;
|
|
using System.IO;
|
|
using System.Text;
|
|
using CommunityToolkit.Mvvm.ComponentModel;
|
|
using CommunityToolkit.Mvvm.Input;
|
|
|
|
namespace Sln.Wcs.UI.ViewModels;
|
|
|
|
public partial class SystemMonitorViewModel : ObservableObject
|
|
{
|
|
[ObservableProperty]
|
|
private ObservableCollection<LogEntry> _logs = new();
|
|
|
|
[ObservableProperty]
|
|
private int _logCount;
|
|
|
|
[ObservableProperty]
|
|
private string _filterText = string.Empty;
|
|
|
|
[ObservableProperty]
|
|
private bool _autoScroll = true;
|
|
|
|
private const int MaxLogs = 5000;
|
|
|
|
public SystemMonitorViewModel()
|
|
{
|
|
// 安装控制台输出拦截器
|
|
var original = Console.Out;
|
|
var writer = new LogTextWriter(original, entry =>
|
|
{
|
|
Avalonia.Threading.Dispatcher.UIThread.Post(() =>
|
|
{
|
|
Logs.Add(entry);
|
|
if (Logs.Count > MaxLogs) Logs.RemoveAt(0);
|
|
LogCount = Logs.Count;
|
|
});
|
|
});
|
|
Console.SetOut(writer);
|
|
}
|
|
|
|
[RelayCommand]
|
|
private void Clear()
|
|
{
|
|
Logs.Clear();
|
|
LogCount = 0;
|
|
}
|
|
|
|
[RelayCommand]
|
|
private void ToggleAutoScroll()
|
|
{
|
|
AutoScroll = !AutoScroll;
|
|
}
|
|
}
|
|
|
|
public class LogEntry
|
|
{
|
|
public DateTime Time { get; set; }
|
|
public string TimeText => Time.ToString("HH:mm:ss.fff");
|
|
public string Message { get; set; } = string.Empty;
|
|
public string Level { get; set; } = "INFO";
|
|
}
|
|
|
|
/// <summary>
|
|
/// 拦截 Console.WriteLine 输出,同时写入原始输出和 ObservableCollection
|
|
/// </summary>
|
|
internal class LogTextWriter : TextWriter
|
|
{
|
|
private readonly TextWriter _original;
|
|
private readonly Action<LogEntry> _onWrite;
|
|
private readonly StringBuilder _buffer = new();
|
|
|
|
public LogTextWriter(TextWriter original, Action<LogEntry> onWrite)
|
|
{
|
|
_original = original;
|
|
_onWrite = onWrite;
|
|
}
|
|
|
|
public override Encoding Encoding => Encoding.UTF8;
|
|
|
|
public override void Write(char value)
|
|
{
|
|
_original.Write(value);
|
|
if (value == '\n')
|
|
{
|
|
FlushBuffer();
|
|
}
|
|
else if (value != '\r')
|
|
{
|
|
_buffer.Append(value);
|
|
}
|
|
}
|
|
|
|
public override void WriteLine(string? message)
|
|
{
|
|
_original.WriteLine(message);
|
|
if (message != null)
|
|
{
|
|
_onWrite(new LogEntry { Time = DateTime.Now, Message = message, Level = "INFO" });
|
|
}
|
|
}
|
|
|
|
private void FlushBuffer()
|
|
{
|
|
var msg = _buffer.ToString();
|
|
_buffer.Clear();
|
|
if (msg.Length > 0)
|
|
{
|
|
_onWrite(new LogEntry { Time = DateTime.Now, Message = msg, Level = "INFO" });
|
|
}
|
|
}
|
|
}
|