feat(ui): add current-launch logs tab
Add Live Chat and Logs tabs to the non-edit left panel. Expose a bounded process-local AppLog feed so the newest messages appear first without importing earlier startup.log contents or changing file logging. Ref: https://obsproject.com/forum/resources/understanding-obs-studio-log.473
This commit is contained in:
@@ -0,0 +1,95 @@
|
||||
using System.Collections.ObjectModel;
|
||||
using System.Linq;
|
||||
using System.Windows.Threading;
|
||||
using ytLive.Helpers;
|
||||
|
||||
namespace ytLive.ViewModels;
|
||||
|
||||
public partial class MainViewModel
|
||||
{
|
||||
private const int VisibleLogEntryLimit = 500;
|
||||
private readonly ObservableCollection<AppLogEntry> _currentLaunchLogEntries = new();
|
||||
private DispatcherTimer? _currentLaunchLogTimer;
|
||||
private long _lastCurrentLaunchLogSequence;
|
||||
private bool _isLogsTabSelected;
|
||||
|
||||
public ObservableCollection<AppLogEntry> CurrentLaunchLogEntries => _currentLaunchLogEntries;
|
||||
|
||||
public bool IsLiveChatTabSelected
|
||||
{
|
||||
get => !_isLogsTabSelected;
|
||||
set
|
||||
{
|
||||
if (value)
|
||||
SelectLogsTab(false);
|
||||
else if (!_isLogsTabSelected)
|
||||
OnPropertyChanged(nameof(IsLiveChatTabSelected));
|
||||
}
|
||||
}
|
||||
|
||||
public bool IsLogsTabSelected
|
||||
{
|
||||
get => _isLogsTabSelected;
|
||||
set
|
||||
{
|
||||
if (value)
|
||||
SelectLogsTab(true);
|
||||
else if (_isLogsTabSelected)
|
||||
OnPropertyChanged(nameof(IsLogsTabSelected));
|
||||
}
|
||||
}
|
||||
|
||||
private void InitializeCurrentLaunchLogs()
|
||||
{
|
||||
foreach (var entry in AppLog.SnapshotCurrentLaunch()
|
||||
.OrderByDescending(entry => entry.Sequence)
|
||||
.Take(VisibleLogEntryLimit))
|
||||
_currentLaunchLogEntries.Add(entry);
|
||||
|
||||
_lastCurrentLaunchLogSequence = _currentLaunchLogEntries.FirstOrDefault()?.Sequence ?? 0;
|
||||
_currentLaunchLogTimer = new DispatcherTimer { Interval = TimeSpan.FromMilliseconds(250) };
|
||||
_currentLaunchLogTimer.Tick += (_, _) => RefreshCurrentLaunchLogs();
|
||||
}
|
||||
|
||||
private void SelectLogsTab(bool selected)
|
||||
{
|
||||
if (_isLogsTabSelected == selected)
|
||||
{
|
||||
OnPropertyChanged(nameof(IsLiveChatTabSelected));
|
||||
OnPropertyChanged(nameof(IsLogsTabSelected));
|
||||
return;
|
||||
}
|
||||
|
||||
_isLogsTabSelected = selected;
|
||||
OnPropertyChanged(nameof(IsLiveChatTabSelected));
|
||||
OnPropertyChanged(nameof(IsLogsTabSelected));
|
||||
if (selected)
|
||||
{
|
||||
RefreshCurrentLaunchLogs();
|
||||
_currentLaunchLogTimer?.Start();
|
||||
}
|
||||
else
|
||||
{
|
||||
_currentLaunchLogTimer?.Stop();
|
||||
}
|
||||
}
|
||||
|
||||
internal void RefreshCurrentLaunchLogs()
|
||||
{
|
||||
var newEntries = AppLog.SnapshotCurrentLaunch()
|
||||
.Where(entry => entry.Sequence > _lastCurrentLaunchLogSequence)
|
||||
.OrderBy(entry => entry.Sequence)
|
||||
.ToArray();
|
||||
|
||||
foreach (var entry in newEntries)
|
||||
{
|
||||
_currentLaunchLogEntries.Insert(0, entry);
|
||||
if (_currentLaunchLogEntries.Count > VisibleLogEntryLimit)
|
||||
_currentLaunchLogEntries.RemoveAt(_currentLaunchLogEntries.Count - 1);
|
||||
_lastCurrentLaunchLogSequence = entry.Sequence;
|
||||
}
|
||||
}
|
||||
|
||||
private void StopCurrentLaunchLogFeed()
|
||||
=> _currentLaunchLogTimer?.Stop();
|
||||
}
|
||||
Reference in New Issue
Block a user