Files
MPF/MPF.UI.Core/UserControls/LogOutput.xaml.cs

242 lines
7.1 KiB
C#
Raw Normal View History

2023-10-07 01:59:28 -04:00
using System;
2023-10-09 11:44:06 -04:00
using System.IO;
2023-10-07 01:59:28 -04:00
using System.Windows;
using System.Windows.Controls;
2023-10-09 11:44:06 -04:00
using System.Windows.Documents;
using System.Windows.Media;
using System.Windows.Threading;
2023-10-07 01:59:28 -04:00
using MPF.Core.Data;
Log Window (#94) * Split type combobox into system combobox and disc type combobox * corrected indentation for xaml file * fixed merge with head * fixed format * fixed issues for PR, added KnownSystem.CUSTOM * removed Updater.cs which ended by error in commit * fixed GetOuptutName() for new drive/system combobox * created LogWindow and first tests of output gathering * integrated all the proof of concept related to stream fetching of DIC output into LogWindow * working on LogWindow\ncreated more efficient output matching management, improved handling of process termination * created Tasks file\nmoved some methods there, created DumpEnvironment to manage are arguments * moved additional methods to Tasks to make it more modular * changed StartDumping flow to avoid returning if extra tools are not found * moved main dump workflow into Tasks class * created specific DumpResult class for better error reporting/management * fixes * fixes Dispatcher thread issue with progress bar * continued refactor - split EnsureDiscInformation into an additional EnsureCorrectInformationForSystemAndMediaType - proof of concept of using custom extensions to enum types to give better functionality (and encapsulation) - changed cmb_MediaType to keep a List<MediaType?> and got rid of Tuple<string, MediaType?> * restored GetDiscType functionality * fixed btn_StartStop enabled on EnsureCorrect... error * fixed whitespace * fixed indentation * merged conflicts * moved log window * working on LogWindow resize/location behavior * working on message logging in LogWindow * added working integration between MenuItem for LogWindow and its visibility status, fixes issues with positioning and visibility, correctly bound Verbose flag to property * finished integrating LogWindow, added some verbose logs * added logs * fixed include order * added option to show log window at startup, removed useless QuietMode property from MainWindow
2018-07-14 00:48:35 +02:00
2023-12-01 23:58:01 -05:00
#pragma warning disable IDE1006 // Naming Styles
2023-09-25 15:43:01 -04:00
namespace MPF.UI.Core.UserControls
Log Window (#94) * Split type combobox into system combobox and disc type combobox * corrected indentation for xaml file * fixed merge with head * fixed format * fixed issues for PR, added KnownSystem.CUSTOM * removed Updater.cs which ended by error in commit * fixed GetOuptutName() for new drive/system combobox * created LogWindow and first tests of output gathering * integrated all the proof of concept related to stream fetching of DIC output into LogWindow * working on LogWindow\ncreated more efficient output matching management, improved handling of process termination * created Tasks file\nmoved some methods there, created DumpEnvironment to manage are arguments * moved additional methods to Tasks to make it more modular * changed StartDumping flow to avoid returning if extra tools are not found * moved main dump workflow into Tasks class * created specific DumpResult class for better error reporting/management * fixes * fixes Dispatcher thread issue with progress bar * continued refactor - split EnsureDiscInformation into an additional EnsureCorrectInformationForSystemAndMediaType - proof of concept of using custom extensions to enum types to give better functionality (and encapsulation) - changed cmb_MediaType to keep a List<MediaType?> and got rid of Tuple<string, MediaType?> * restored GetDiscType functionality * fixed btn_StartStop enabled on EnsureCorrect... error * fixed whitespace * fixed indentation * merged conflicts * moved log window * working on LogWindow resize/location behavior * working on message logging in LogWindow * added working integration between MenuItem for LogWindow and its visibility status, fixes issues with positioning and visibility, correctly bound Verbose flag to property * finished integrating LogWindow, added some verbose logs * added logs * fixed include order * added option to show log window at startup, removed useless QuietMode property from MainWindow
2018-07-14 00:48:35 +02:00
{
2021-02-28 02:28:53 -08:00
public partial class LogOutput : UserControl
Log Window (#94) * Split type combobox into system combobox and disc type combobox * corrected indentation for xaml file * fixed merge with head * fixed format * fixed issues for PR, added KnownSystem.CUSTOM * removed Updater.cs which ended by error in commit * fixed GetOuptutName() for new drive/system combobox * created LogWindow and first tests of output gathering * integrated all the proof of concept related to stream fetching of DIC output into LogWindow * working on LogWindow\ncreated more efficient output matching management, improved handling of process termination * created Tasks file\nmoved some methods there, created DumpEnvironment to manage are arguments * moved additional methods to Tasks to make it more modular * changed StartDumping flow to avoid returning if extra tools are not found * moved main dump workflow into Tasks class * created specific DumpResult class for better error reporting/management * fixes * fixes Dispatcher thread issue with progress bar * continued refactor - split EnsureDiscInformation into an additional EnsureCorrectInformationForSystemAndMediaType - proof of concept of using custom extensions to enum types to give better functionality (and encapsulation) - changed cmb_MediaType to keep a List<MediaType?> and got rid of Tuple<string, MediaType?> * restored GetDiscType functionality * fixed btn_StartStop enabled on EnsureCorrect... error * fixed whitespace * fixed indentation * merged conflicts * moved log window * working on LogWindow resize/location behavior * working on message logging in LogWindow * added working integration between MenuItem for LogWindow and its visibility status, fixes issues with positioning and visibility, correctly bound Verbose flag to property * finished integrating LogWindow, added some verbose logs * added logs * fixed include order * added option to show log window at startup, removed useless QuietMode property from MainWindow
2018-07-14 00:48:35 +02:00
{
/// <summary>
2023-10-09 11:44:06 -04:00
/// Document representing the text
/// </summary>
2023-10-09 11:44:06 -04:00
internal FlowDocument Document { get; private set; }
/// <summary>
/// Queue of items that need to be logged
/// </summary>
internal ProcessingQueue<LogLine> LogQueue { get; private set; }
/// <summary>
/// Paragraph backing the log
/// </summary>
private readonly Paragraph _paragraph;
/// <summary>
/// Cached value of the last line written
/// </summary>
2023-10-11 11:49:56 -04:00
private Run? lastLine = null;
2021-03-10 19:11:31 -08:00
2023-11-30 23:34:44 -05:00
#if NET35
private Button? _ClearButton => ItemHelper.FindChild<Button>(this, "ClearButton");
private RichTextBox? _Output => ItemHelper.FindChild<RichTextBox>(this, "Output");
private ScrollViewer? _OutputViewer => ItemHelper.FindChild<ScrollViewer>(this, "OutputViewer");
private Button? _SaveButton => ItemHelper.FindChild<Button>(this, "SaveButton");
#endif
2021-02-28 02:28:53 -08:00
public LogOutput()
Log Window (#94) * Split type combobox into system combobox and disc type combobox * corrected indentation for xaml file * fixed merge with head * fixed format * fixed issues for PR, added KnownSystem.CUSTOM * removed Updater.cs which ended by error in commit * fixed GetOuptutName() for new drive/system combobox * created LogWindow and first tests of output gathering * integrated all the proof of concept related to stream fetching of DIC output into LogWindow * working on LogWindow\ncreated more efficient output matching management, improved handling of process termination * created Tasks file\nmoved some methods there, created DumpEnvironment to manage are arguments * moved additional methods to Tasks to make it more modular * changed StartDumping flow to avoid returning if extra tools are not found * moved main dump workflow into Tasks class * created specific DumpResult class for better error reporting/management * fixes * fixes Dispatcher thread issue with progress bar * continued refactor - split EnsureDiscInformation into an additional EnsureCorrectInformationForSystemAndMediaType - proof of concept of using custom extensions to enum types to give better functionality (and encapsulation) - changed cmb_MediaType to keep a List<MediaType?> and got rid of Tuple<string, MediaType?> * restored GetDiscType functionality * fixed btn_StartStop enabled on EnsureCorrect... error * fixed whitespace * fixed indentation * merged conflicts * moved log window * working on LogWindow resize/location behavior * working on message logging in LogWindow * added working integration between MenuItem for LogWindow and its visibility status, fixes issues with positioning and visibility, correctly bound Verbose flag to property * finished integrating LogWindow, added some verbose logs * added logs * fixed include order * added option to show log window at startup, removed useless QuietMode property from MainWindow
2018-07-14 00:48:35 +02:00
{
2023-11-30 23:34:44 -05:00
#if NET40_OR_GREATER || NETCOREAPP
Log Window (#94) * Split type combobox into system combobox and disc type combobox * corrected indentation for xaml file * fixed merge with head * fixed format * fixed issues for PR, added KnownSystem.CUSTOM * removed Updater.cs which ended by error in commit * fixed GetOuptutName() for new drive/system combobox * created LogWindow and first tests of output gathering * integrated all the proof of concept related to stream fetching of DIC output into LogWindow * working on LogWindow\ncreated more efficient output matching management, improved handling of process termination * created Tasks file\nmoved some methods there, created DumpEnvironment to manage are arguments * moved additional methods to Tasks to make it more modular * changed StartDumping flow to avoid returning if extra tools are not found * moved main dump workflow into Tasks class * created specific DumpResult class for better error reporting/management * fixes * fixes Dispatcher thread issue with progress bar * continued refactor - split EnsureDiscInformation into an additional EnsureCorrectInformationForSystemAndMediaType - proof of concept of using custom extensions to enum types to give better functionality (and encapsulation) - changed cmb_MediaType to keep a List<MediaType?> and got rid of Tuple<string, MediaType?> * restored GetDiscType functionality * fixed btn_StartStop enabled on EnsureCorrect... error * fixed whitespace * fixed indentation * merged conflicts * moved log window * working on LogWindow resize/location behavior * working on message logging in LogWindow * added working integration between MenuItem for LogWindow and its visibility status, fixes issues with positioning and visibility, correctly bound Verbose flag to property * finished integrating LogWindow, added some verbose logs * added logs * fixed include order * added option to show log window at startup, removed useless QuietMode property from MainWindow
2018-07-14 00:48:35 +02:00
InitializeComponent();
2023-11-30 23:34:44 -05:00
#endif
2023-10-09 11:44:06 -04:00
// Update the internal state
Document = new FlowDocument()
{
Background = new SolidColorBrush(Color.FromArgb(0xFF, 0x20, 0x20, 0x20))
};
_paragraph = new Paragraph();
Document.Blocks.Add(_paragraph);
// Setup the processing queue
LogQueue = new ProcessingQueue<LogLine>(ProcessLogLine);
2023-10-07 01:59:28 -04:00
// Add handlers
2023-11-30 23:34:44 -05:00
#if NET35
_OutputViewer!.SizeChanged += OutputViewerSizeChanged;
_Output!.TextChanged += OnTextChanged;
_ClearButton!.Click += OnClearButton;
_SaveButton!.Click += OnSaveButton;
#else
2023-10-07 01:59:28 -04:00
OutputViewer.SizeChanged += OutputViewerSizeChanged;
Output.TextChanged += OnTextChanged;
ClearButton.Click += OnClearButton;
SaveButton.Click += OnSaveButton;
2023-11-30 23:34:44 -05:00
#endif
2023-10-07 01:59:28 -04:00
// Update the internal state
2023-11-30 23:34:44 -05:00
#if NET35
_Output.Document = Document;
#else
2023-10-09 11:44:06 -04:00
Output.Document = Document;
2023-11-30 23:34:44 -05:00
#endif
2023-10-07 01:59:28 -04:00
}
#region Logging
/// <summary>
/// Enqueue text to the log with formatting
/// </summary>
/// <param name="logLevel">LogLevel for the log</param>
/// <param name="text">Text to write to the log</param>
public void EnqueueLog(LogLevel logLevel, string text)
2023-10-07 01:59:28 -04:00
{
// Null text gets ignored
if (text == null)
return;
// Enqueue the text
2023-10-09 11:44:06 -04:00
LogQueue.Enqueue(new LogLine(text, logLevel));
}
/// <summary>
/// Log line wrapper
/// </summary>
internal readonly struct LogLine
{
public readonly string Text;
public readonly LogLevel LogLevel;
public LogLine(string text, LogLevel logLevel)
{
this.Text = text;
this.LogLevel = logLevel;
}
/// <summary>
/// Get the foreground Brush for the current LogLevel
/// </summary>
/// <returns>Brush representing the color</returns>
public Brush GetForegroundColor()
{
2023-12-01 23:58:01 -05:00
return this.LogLevel switch
2023-10-09 11:44:06 -04:00
{
2023-12-01 23:58:01 -05:00
LogLevel.SECRET => Brushes.Blue,
LogLevel.ERROR => Brushes.Red,
LogLevel.VERBOSE => Brushes.Yellow,
_ => Brushes.White,
};
2023-10-09 11:44:06 -04:00
}
/// <summary>
/// Generate a Run object from the current LogLine
/// </summary>
/// <returns>Run object based on internal values</returns>
public Run GenerateRun()
{
return new Run { Text = this.Text, Foreground = GetForegroundColor() };
}
}
/// <summary>
/// Process the log lines in the queue
/// </summary>
/// <param name="nextLogLine">LogLine item to process</param>
internal void ProcessLogLine(LogLine nextLogLine)
{
// Null text gets ignored
string nextText = nextLogLine.Text;
if (nextText == null)
return;
try
{
if (nextText.StartsWith("\r"))
ReplaceLastLine(nextLogLine);
else
AppendToTextBox(nextLogLine);
}
catch (Exception ex)
{
// In the event that something fails horribly, we want to log
AppendToTextBox(new LogLine(ex.ToString(), LogLevel.ERROR));
}
}
/// <summary>
/// Append log line to the log text box
/// </summary>
/// <param name="logLine">LogLine value to append</param>
private void AppendToTextBox(LogLine logLine)
{
Dispatcher.Invoke(() =>
{
var run = logLine.GenerateRun();
_paragraph.Inlines.Add(run);
lastLine = run;
});
}
/// <summary>
/// Replace the last line written to the log text box
/// </summary>
/// <param name="logLine">LogLine value to append</param>
private void ReplaceLastLine(LogLine logLine)
{
Dispatcher.Invoke(() =>
{
2023-10-11 12:37:31 -04:00
lastLine ??= new Run();
2023-10-09 11:44:06 -04:00
lastLine.Text = logLine.Text;
lastLine.Foreground = logLine.GetForegroundColor();
});
2023-10-07 01:59:28 -04:00
}
2023-11-30 23:34:44 -05:00
#endregion
2023-10-07 01:59:28 -04:00
#region Helpers
2023-10-09 11:44:06 -04:00
/// <summary>
/// Clear all inlines of the paragraph
/// </summary>
private void ClearInlines() => _paragraph.Inlines.Clear();
/// <summary>
/// Save all inlines to console.log
/// </summary>
private void SaveInlines()
{
2023-12-01 23:58:01 -05:00
using var sw = new StreamWriter(File.OpenWrite("console.log"));
foreach (var inline in _paragraph.Inlines)
2023-10-09 11:44:06 -04:00
{
2023-12-01 23:58:01 -05:00
if (inline is Run run)
sw.Write(run.Text);
2023-10-09 11:44:06 -04:00
}
}
2023-10-07 01:59:28 -04:00
/// <summary>
/// Scroll the current view to the bottom
/// </summary>
2023-11-30 23:34:44 -05:00
#if NET35
public void ScrollToBottom() => _OutputViewer!.ScrollToBottom();
#else
2023-10-07 01:59:28 -04:00
public void ScrollToBottom() => OutputViewer.ScrollToBottom();
2023-11-30 23:34:44 -05:00
#endif
2023-10-07 01:59:28 -04:00
#endregion
#region EventHandlers
private void OnClearButton(object sender, EventArgs e)
2023-10-09 11:44:06 -04:00
=> ClearInlines();
2023-10-07 01:59:28 -04:00
private void OnSaveButton(object sender, EventArgs e)
2023-10-09 11:44:06 -04:00
=> SaveInlines();
2023-10-07 01:59:28 -04:00
private void OnTextChanged(object sender, TextChangedEventArgs e)
=> ScrollToBottom();
private void OutputViewerSizeChanged(object sender, SizeChangedEventArgs e)
=> ScrollToBottom();
#endregion
Log Window (#94) * Split type combobox into system combobox and disc type combobox * corrected indentation for xaml file * fixed merge with head * fixed format * fixed issues for PR, added KnownSystem.CUSTOM * removed Updater.cs which ended by error in commit * fixed GetOuptutName() for new drive/system combobox * created LogWindow and first tests of output gathering * integrated all the proof of concept related to stream fetching of DIC output into LogWindow * working on LogWindow\ncreated more efficient output matching management, improved handling of process termination * created Tasks file\nmoved some methods there, created DumpEnvironment to manage are arguments * moved additional methods to Tasks to make it more modular * changed StartDumping flow to avoid returning if extra tools are not found * moved main dump workflow into Tasks class * created specific DumpResult class for better error reporting/management * fixes * fixes Dispatcher thread issue with progress bar * continued refactor - split EnsureDiscInformation into an additional EnsureCorrectInformationForSystemAndMediaType - proof of concept of using custom extensions to enum types to give better functionality (and encapsulation) - changed cmb_MediaType to keep a List<MediaType?> and got rid of Tuple<string, MediaType?> * restored GetDiscType functionality * fixed btn_StartStop enabled on EnsureCorrect... error * fixed whitespace * fixed indentation * merged conflicts * moved log window * working on LogWindow resize/location behavior * working on message logging in LogWindow * added working integration between MenuItem for LogWindow and its visibility status, fixes issues with positioning and visibility, correctly bound Verbose flag to property * finished integrating LogWindow, added some verbose logs * added logs * fixed include order * added option to show log window at startup, removed useless QuietMode property from MainWindow
2018-07-14 00:48:35 +02:00
}
}