Files
JMR-devandCopilot 73a81138a7 Add plot legend with floating top-right overlay
Renders a small panel inside the plot showing each visible series as [color swatch] [sensor title] [latest value + unit]. Panel width fits the longest sensor name and redraws when sensors are added or removed from the plot (RefreshPlotSeries already fires PlotInvalidated). Falls back to ellipsizing only if the label column would push the panel past the plot bounds. Capped at 12 rows with a +N more footer; auto-hides when plot pane is narrower than 200px. Theme-aware translucent background + border match the plot frame.

Persisted as showPlotLegend (default true) and toggleable from View menu and plot context menu. The View menu item is hidden when ShowPlot is off, but the setting itself is preserved across plot enable/disable and app restarts.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-06-02 14:26:11 -05:00

154 lines
9.5 KiB
XML

<!-- This Source Code Form is subject to the terms of the Mozilla Public License, v. 2.0.
If a copy of the MPL was not distributed with this file, You can obtain one at http://mozilla.org/MPL/2.0/.
Copyright (C) LibreHardwareMonitor and Contributors. -->
<Window
x:Class="LibreHardwareMonitor.Windows.WinUI.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="using:LibreHardwareMonitor.Windows.WinUI"
xmlns:controls="using:LibreHardwareMonitor.Windows.WinUI.Controls">
<Grid x:Name="RootGrid">
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="*" />
<RowDefinition Height="Auto" />
</Grid.RowDefinitions>
<MenuBar x:Name="AppMenuBar"
Grid.Row="0"
IsEnabled="{x:Bind ViewModel.IsHardwareInteractionEnabled, Mode=OneWay}">
<MenuBarItem Title="File">
<MenuFlyoutItem Text="Save Report..." Click="OnSaveReport" />
<MenuFlyoutSeparator />
<MenuFlyoutItem Text="Reset" Click="OnResetHardware" />
<MenuFlyoutSubItem Text="Hardware">
<ToggleMenuFlyoutItem Text="Motherboard" IsChecked="{x:Bind ViewModel.IsMotherboardEnabled, Mode=TwoWay}" />
<ToggleMenuFlyoutItem Text="CPU" IsChecked="{x:Bind ViewModel.IsCpuEnabled, Mode=TwoWay}" />
<ToggleMenuFlyoutItem Text="Memory" IsChecked="{x:Bind ViewModel.IsMemoryEnabled, Mode=TwoWay}" />
<ToggleMenuFlyoutItem Text="GPU" IsChecked="{x:Bind ViewModel.IsGpuEnabled, Mode=TwoWay}" />
<ToggleMenuFlyoutItem Text="Power Monitors" IsChecked="{x:Bind ViewModel.IsPowerMonitorEnabled, Mode=TwoWay}" />
<ToggleMenuFlyoutItem Text="Fan Controllers" IsChecked="{x:Bind ViewModel.IsControllerEnabled, Mode=TwoWay}" />
<ToggleMenuFlyoutItem Text="Storage Devices" IsChecked="{x:Bind ViewModel.IsStorageEnabled, Mode=TwoWay}" />
<ToggleMenuFlyoutItem Text="Network" IsChecked="{x:Bind ViewModel.IsNetworkEnabled, Mode=TwoWay}" />
<ToggleMenuFlyoutItem Text="Power Supplies" IsChecked="{x:Bind ViewModel.IsPsuEnabled, Mode=TwoWay}" />
<ToggleMenuFlyoutItem Text="Battery" IsChecked="{x:Bind ViewModel.IsBatteryEnabled, Mode=TwoWay}" />
</MenuFlyoutSubItem>
<MenuFlyoutSeparator />
<MenuFlyoutItem Text="Exit" Click="OnExit" />
</MenuBarItem>
<MenuBarItem Title="View">
<MenuFlyoutItem Text="Reset Min/Max" Click="OnResetMinMax" />
<MenuFlyoutItem Text="Expand All Nodes" Click="OnExpandAll" />
<MenuFlyoutItem Text="Collapse All Nodes" Click="OnCollapseAll" />
<MenuFlyoutItem Text="Reset Plot" Click="OnResetPlot" />
<MenuFlyoutSeparator />
<ToggleMenuFlyoutItem Text="Show Hidden Sensors" IsChecked="{x:Bind ViewModel.ShowHiddenSensors, Mode=TwoWay}" />
<ToggleMenuFlyoutItem Text="Show Plot" IsChecked="{x:Bind ViewModel.ShowPlot, Mode=TwoWay}" />
<ToggleMenuFlyoutItem Text="Show Plot Legend"
IsChecked="{x:Bind ViewModel.ShowPlotLegend, Mode=TwoWay}"
Visibility="{x:Bind ViewModel.ShowPlotLegendMenuVisibility, Mode=OneWay}" />
<ToggleMenuFlyoutItem Text="Gadget" IsChecked="{x:Bind ViewModel.ShowGadget, Mode=TwoWay}" />
<MenuFlyoutSubItem Text="Columns">
<ToggleMenuFlyoutItem Text="Value" IsChecked="{x:Bind ViewModel.ShowValueColumn, Mode=TwoWay}" />
<ToggleMenuFlyoutItem Text="Min" IsChecked="{x:Bind ViewModel.ShowMinColumn, Mode=TwoWay}" />
<ToggleMenuFlyoutItem Text="Max" IsChecked="{x:Bind ViewModel.ShowMaxColumn, Mode=TwoWay}" />
</MenuFlyoutSubItem>
</MenuBarItem>
<MenuBarItem Title="Options">
<ToggleMenuFlyoutItem Text="Start Minimized" IsChecked="{x:Bind ViewModel.StartMinimized, Mode=TwoWay}" />
<ToggleMenuFlyoutItem Text="Minimize To Tray" IsChecked="{x:Bind ViewModel.MinimizeToTray, Mode=TwoWay}" />
<ToggleMenuFlyoutItem Text="Minimize On Close" IsChecked="{x:Bind ViewModel.MinimizeOnClose, Mode=TwoWay}" />
<ToggleMenuFlyoutItem Text="Run On Windows Startup" IsChecked="{x:Bind ViewModel.RunOnStartup, Mode=TwoWay}" />
<MenuFlyoutSeparator />
<MenuFlyoutSubItem x:Name="TemperatureUnitMenu" Text="Temperature Unit" />
<MenuFlyoutSubItem x:Name="PlotLocationMenu" Text="Plot Location" />
<MenuFlyoutSubItem x:Name="ThemeMenu" Text="Theme" />
<MenuFlyoutSubItem x:Name="StrokeThicknessMenu" Text="Stroke Thickness" />
<MenuFlyoutSeparator />
<ToggleMenuFlyoutItem Text="Log Sensors" IsChecked="{x:Bind ViewModel.LogSensors, Mode=TwoWay}" />
<ToggleMenuFlyoutItem Text="Force Drive Wakeup" IsChecked="{x:Bind ViewModel.ForceDriveWakeup, Mode=TwoWay}" />
<ToggleMenuFlyoutItem Text="Throttle ATA Storage" IsChecked="{x:Bind ViewModel.ThrottleAtaUpdate, Mode=TwoWay}" />
<MenuFlyoutSubItem x:Name="FileRotationMenu" Text="File Rotation Method" />
<MenuFlyoutSubItem x:Name="UpdateIntervalMenu" Text="Update Interval" />
<MenuFlyoutSubItem x:Name="LoggingIntervalMenu" Text="Logging Interval" />
<MenuFlyoutSubItem x:Name="SensorTimeWindowMenu" Text="Sensor Values Time Window" />
<MenuFlyoutSeparator />
<MenuFlyoutSubItem Text="Remote Web Server">
<ToggleMenuFlyoutItem x:Name="RunWebServerItem" Text="Run" IsChecked="{x:Bind ViewModel.RunWebServer, Mode=TwoWay}" />
<MenuFlyoutItem x:Name="WebServerInterfaceItem" Text="Interface / Port" Click="OnWebServerSettings" />
<MenuFlyoutItem x:Name="WebServerAuthItem" Text="Authentication" Click="OnWebServerAuthentication" />
</MenuFlyoutSubItem>
</MenuBarItem>
<MenuBarItem Title="Help">
<MenuFlyoutItem Text="About" Click="OnAbout" />
</MenuBarItem>
</MenuBar>
<Grid x:Name="ContentGrid" Grid.Row="1">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*" />
<ColumnDefinition Width="320" />
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height="*" />
<RowDefinition Height="220" />
</Grid.RowDefinitions>
<Grid x:Name="SensorPane" Grid.Column="0" Grid.Row="0">
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<Grid x:Name="SensorHeaderHost" Grid.Row="0" />
<Grid Grid.Row="1">
<TreeView x:Name="SensorTree"
SelectionMode="Single"
SelectionChanged="SensorTree_SelectionChanged">
<TreeView.ItemTemplate>
<DataTemplate>
<ContentPresenter Content="{Binding Content}" />
</DataTemplate>
</TreeView.ItemTemplate>
</TreeView>
</Grid>
</Grid>
<Grid x:Name="PlotPane"
Grid.Column="1"
Grid.Row="0"
Padding="8"
BorderThickness="1,0,0,0"
BorderBrush="{ThemeResource DividerStrokeColorDefaultBrush}">
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<Grid Grid.Row="0">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*" />
<ColumnDefinition Width="Auto" />
</Grid.ColumnDefinitions>
<TextBlock Text="Plot" FontWeight="SemiBold" VerticalAlignment="Center" />
<Button Grid.Column="1" Content="Reset" Click="OnResetPlot" />
</Grid>
<controls:PlotView x:Name="PlotControl" Grid.Row="1" />
</Grid>
</Grid>
<TextBlock x:Name="StatusText"
Grid.Row="2"
Padding="8,4,8,4"
TextTrimming="CharacterEllipsis"
Text="{x:Bind ViewModel.StatusText, Mode=OneWay}" />
<Grid x:Name="OverlayHost"
Grid.RowSpan="3"
IsHitTestVisible="True"
Visibility="{x:Bind ViewModel.HardwareLoadingVisibility, Mode=OneWay}">
<Grid.Background>
<SolidColorBrush Color="#80808080" />
</Grid.Background>
<StackPanel HorizontalAlignment="Center" VerticalAlignment="Center" Spacing="12">
<ProgressRing Width="64" Height="64" IsIndeterminate="True" />
<TextBlock Text="Loading hardware devices..."
FontWeight="SemiBold"
HorizontalAlignment="Center" />
</StackPanel>
</Grid>
</Grid>
</Window>