A:动态的悬浮窗大小管理以及信息分析窗口设置

This commit is contained in:
jimmy committed 2025-07-27 16:35:44 +08:00
1 parent 53fa1aa4af
commit 66d535d1f8
4 files changed
+57 -180

No files matched your search

@@ -8,8 +8,7 @@
xmlns:userControls="clr-namespace:Shell.UserControls"
mc:Ignorable="d"
Title="NetVizor - 网速监控"
Height="70"
Width="120"
SizeToContent="WidthAndHeight"
WindowStyle="None"
AllowsTransparency="True"
Background="Transparent"
@@ -266,15 +266,12 @@ public partial class NetView : Window
_showDetailedInfo = !_showDetailedInfo;
DetailedInfoMenuItem.IsChecked = _showDetailedInfo;
// Toggle window height for detailed info
if (_showDetailedInfo)
{
this.Height = 200; // Expanded height for detailed info
}
else
{
this.Height = 120; // Compact height
}
// The window will automatically resize based on content
// No need to manually set height anymore due to SizeToContent="WidthAndHeight"
// You can trigger a re-layout if needed
this.InvalidateMeasure();
this.UpdateLayout();
}
private void HideToTray_Click(object sender, RoutedEventArgs e)
@@ -305,17 +302,6 @@ public partial class NetView : Window
}
}
protected override void OnLocationChanged(EventArgs e)
{
base.OnLocationChanged(e);
// Snap to screen if enabled
if (_snapToScreen && !_isPositionLocked)
{
SnapToScreen();
}
}
// Handle window dragging
private void Grid_MouseLeftButtonDown(object sender, System.Windows.Input.MouseButtonEventArgs e)
{
@@ -325,9 +311,6 @@ public partial class NetView : Window
try
{
this.DragMove();
// After drag move, check and snap back if outside screen bounds
SnapBackToScreen();
}
catch (InvalidOperationException)
{
@@ -337,6 +320,45 @@ public partial class NetView : Window
}
}
protected override void OnLocationChanged(EventArgs e)
{
base.OnLocationChanged(e);
// Only check snap to screen if that option is enabled
if (_snapToScreen && !_isPositionLocked)
{
SnapToScreen();
}
// Perform boundary check after drag is complete (with delay to avoid flicker)
if (!_isPositionLocked)
{
CheckBoundariesDelayed();
}
}
private System.Windows.Threading.DispatcherTimer? _boundaryCheckTimer;
private void CheckBoundariesDelayed()
{
// Cancel previous timer if exists
_boundaryCheckTimer?.Stop();
// Create new timer for delayed boundary check
_boundaryCheckTimer = new System.Windows.Threading.DispatcherTimer
{
Interval = TimeSpan.FromMilliseconds(150) // Delay to avoid flicker during drag
};
_boundaryCheckTimer.Tick += (s, e) =>
{
_boundaryCheckTimer.Stop();
SnapBackToScreen();
};
_boundaryCheckTimer.Start();
}
private void SnapBackToScreen()
{
var workArea = SystemParameters.WorkArea;
@@ -14,78 +14,5 @@
WindowStartupLocation="CenterScreen"
Icon="pack://application:,,,/Assets/Icons/app.ico">
<Window.Resources>
<Style x:Key="ModernWindowStyle" TargetType="Window">
<Setter Property="Background" Value="#F5F5F5"/>
<Setter Property="BorderBrush" Value="#E0E0E0"/>
<Setter Property="BorderThickness" Value="1"/>
</Style>
</Window.Resources>
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="*"/>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<!-- Header -->
<Border Grid.Row="0" Background="#2C3E50" Padding="15,10">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto"/>
<ColumnDefinition Width="*"/>
<ColumnDefinition Width="Auto"/>
</Grid.ColumnDefinitions>
<StackPanel Grid.Column="0" Orientation="Horizontal">
<TextBlock Text="" FontFamily="Segoe Fluent Icons"
FontSize="20" Foreground="White"
VerticalAlignment="Center" Margin="0,0,10,0"/>
<TextBlock Text="流量统计与分析" FontSize="18"
FontWeight="SemiBold" Foreground="White"
VerticalAlignment="Center"/>
</StackPanel>
<TextBlock Grid.Column="1" Text="网络流量实时监控与深度分析"
FontSize="12" Foreground="#BDC3C7"
VerticalAlignment="Center" HorizontalAlignment="Center"/>
<StackPanel Grid.Column="2" Orientation="Horizontal">
<Button Content="刷新" Click="Refresh_Click"
Style="{DynamicResource ModernButtonStyle}"
Margin="0,0,10,0" Padding="10,5"/>
<Button Content="关闭" Click="Close_Click"
Style="{DynamicResource ModernButtonStyle}"
Padding="10,5"/>
</StackPanel>
</Grid>
</Border>
<!-- Main Content - WebPanel -->
<Border Grid.Row="1" Background="White" BorderBrush="#E0E0E0" BorderThickness="0,1,0,1">
<userControls:WebPanel x:Name="WebPanel" />
</Border>
<!-- Footer -->
<Border Grid.Row="2" Background="#34495E" Padding="10,5">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="*"/>
<ColumnDefinition Width="Auto"/>
</Grid.ColumnDefinitions>
<TextBlock Grid.Column="0" Text="需要管理员权限以获取完整的网络统计信息"
FontSize="11" Foreground="#BDC3C7"
VerticalAlignment="Center"/>
<StackPanel Grid.Column="1" Orientation="Horizontal">
<TextBlock Text="状态: " FontSize="11" Foreground="#BDC3C7"
VerticalAlignment="Center"/>
<TextBlock x:Name="StatusText" Text="正在加载..." FontSize="11"
Foreground="#27AE60" VerticalAlignment="Center"/>
</StackPanel>
</Grid>
</Border>
</Grid>
<userControls:WebPanel x:Name="WebPanel" />
</Window>
@@ -3,7 +3,6 @@ using System.Diagnostics;
using System.Runtime.InteropServices;
using System.Security.Principal;
using System.Windows;
using System.Windows.Threading;
using Common.Logger;
namespace Shell.Views;
@@ -12,11 +11,11 @@ public partial class TrafficAnalysisWindow : Window
{
private static TrafficAnalysisWindow? _instance;
private static bool _hasRequestedElevation = false;
// Win32 API for checking admin rights
[DllImport("shell32.dll")]
static extern bool IsUserAnAdmin();
public static TrafficAnalysisWindow Instance
{
get
@@ -29,7 +28,7 @@ public partial class TrafficAnalysisWindow : Window
return _instance;
}
}
private TrafficAnalysisWindow()
{
InitializeComponent();
@@ -38,7 +37,7 @@ public partial class TrafficAnalysisWindow : Window
Log.Info("TrafficAnalysisWindow 初始化");
}
public static void ShowWindow()
{
try
@@ -76,7 +75,7 @@ public partial class TrafficAnalysisWindow : Window
MessageBoxButton.OK, MessageBoxImage.Error);
}
}
private static bool IsRunningAsAdmin()
{
try
@@ -91,7 +90,7 @@ public partial class TrafficAnalysisWindow : Window
return principal.IsInRole(WindowsBuiltInRole.Administrator);
}
}
private static void RequestElevation()
{
try
@@ -117,48 +116,12 @@ public partial class TrafficAnalysisWindow : Window
_hasRequestedElevation = true; // Don't ask again in this session
}
}
private void TrafficAnalysisWindow_Loaded(object sender, RoutedEventArgs e)
{
Log.Info("TrafficAnalysisWindow 加载完成");
// Update status based on admin rights
UpdateStatus();
// Initialize WebPanel if needed
InitializeWebPanel();
}
private void UpdateStatus()
{
if (IsRunningAsAdmin())
{
StatusText.Text = "管理员模式 - 完整功能可用";
StatusText.Foreground = new System.Windows.Media.SolidColorBrush(System.Windows.Media.Colors.Green);
}
else
{
StatusText.Text = "普通模式 - 功能受限";
StatusText.Foreground = new System.Windows.Media.SolidColorBrush(System.Windows.Media.Colors.Orange);
}
}
private void InitializeWebPanel()
{
try
{
// WebPanel should automatically load the Vue3 application
// The WebView2 control will handle the web content
Log.Info("WebPanel 初始化完成");
}
catch (Exception ex)
{
Log.Error4Ctx($"WebPanel 初始化失败: {ex.Message}");
StatusText.Text = "初始化失败";
StatusText.Foreground = new System.Windows.Media.SolidColorBrush(System.Windows.Media.Colors.Red);
}
}
private void TrafficAnalysisWindow_Closing(object sender, CancelEventArgs e)
{
// Don't actually close, just hide the window for better performance
@@ -166,41 +129,7 @@ public partial class TrafficAnalysisWindow : Window
this.Hide();
Log.Info("TrafficAnalysisWindow 隐藏");
}
private void Refresh_Click(object sender, RoutedEventArgs e)
{
try
{
// Refresh the WebPanel content
if (WebPanel != null)
{
// The WebPanel should handle its own refresh logic
Log.Info("刷新流量分析数据");
StatusText.Text = "正在刷新...";
// Use a timer to reset status after refresh
var timer = new DispatcherTimer { Interval = TimeSpan.FromSeconds(2) };
timer.Tick += (s, args) =>
{
UpdateStatus();
timer.Stop();
};
timer.Start();
}
}
catch (Exception ex)
{
Log.Error4Ctx($"刷新失败: {ex.Message}");
System.Windows.MessageBox.Show($"刷新失败: {ex.Message}", "错误",
MessageBoxButton.OK, MessageBoxImage.Error);
}
}
private void Close_Click(object sender, RoutedEventArgs e)
{
this.Hide();
}
// Force close method for application shutdown
public void ForceClose()
{
@@ -208,4 +137,4 @@ public partial class TrafficAnalysisWindow : Window
this.Close();
_instance = null;
}
}
}