1145141919810
代码清理
This commit is contained in:
@@ -732,9 +732,9 @@ namespace Ink_Canvas.Helpers
|
||||
/// </summary>
|
||||
public class AdvancedBezierSmoothing
|
||||
{
|
||||
public double SmoothingStrength { get; set; } = 0.6;
|
||||
public double ResampleInterval { get; set; } = 2.0;
|
||||
public int InterpolationSteps { get; set; } = 12;
|
||||
public double SmoothingStrength { get; set; } = 0.6;
|
||||
public double ResampleInterval { get; set; } = 2.0;
|
||||
public int InterpolationSteps { get; set; } = 12;
|
||||
|
||||
public Stroke SmoothStroke(Stroke stroke)
|
||||
{
|
||||
@@ -764,7 +764,7 @@ namespace Ink_Canvas.Helpers
|
||||
{
|
||||
DrawingAttributes = stroke.DrawingAttributes.Clone()
|
||||
};
|
||||
|
||||
|
||||
System.Diagnostics.Debug.WriteLine($"AdvancedBezierSmoothing: 创建平滑笔画成功");
|
||||
return smoothedStroke;
|
||||
}
|
||||
@@ -797,7 +797,7 @@ namespace Ink_Canvas.Helpers
|
||||
|
||||
// 只生成2-3个插值点
|
||||
int steps = 2;
|
||||
|
||||
|
||||
// 生成贝塞尔曲线点
|
||||
for (int j = 1; j <= steps; j++)
|
||||
{
|
||||
@@ -808,7 +808,7 @@ namespace Ink_Canvas.Helpers
|
||||
}
|
||||
|
||||
result.Add(points[points.Length - 1]);
|
||||
|
||||
|
||||
// 去重处理
|
||||
return RemoveDuplicatePoints(result.ToArray());
|
||||
}
|
||||
@@ -827,10 +827,10 @@ namespace Ink_Canvas.Helpers
|
||||
{
|
||||
var lastPoint = result[result.Count - 1];
|
||||
var currentPoint = points[i];
|
||||
|
||||
double distance = Math.Sqrt(Math.Pow(currentPoint.X - lastPoint.X, 2) +
|
||||
|
||||
double distance = Math.Sqrt(Math.Pow(currentPoint.X - lastPoint.X, 2) +
|
||||
Math.Pow(currentPoint.Y - lastPoint.Y, 2));
|
||||
|
||||
|
||||
if (distance > minDistance)
|
||||
{
|
||||
result.Add(currentPoint);
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
using Ink_Canvas.Helpers;
|
||||
using Newtonsoft.Json;
|
||||
using System;
|
||||
using System.IO;
|
||||
|
||||
@@ -31,22 +31,22 @@ namespace Ink_Canvas.Helpers
|
||||
public FilterInfo CurrentCamera { get; private set; }
|
||||
|
||||
// 新增属性
|
||||
public int RotationAngle
|
||||
{
|
||||
get => _rotationAngle;
|
||||
set => _rotationAngle = Math.Max(0, Math.Min(3, value));
|
||||
public int RotationAngle
|
||||
{
|
||||
get => _rotationAngle;
|
||||
set => _rotationAngle = Math.Max(0, Math.Min(3, value));
|
||||
}
|
||||
|
||||
public int ResolutionWidth
|
||||
{
|
||||
get => _resolutionWidth;
|
||||
set => _resolutionWidth = Math.Max(320, Math.Min(1920, value));
|
||||
|
||||
public int ResolutionWidth
|
||||
{
|
||||
get => _resolutionWidth;
|
||||
set => _resolutionWidth = Math.Max(320, Math.Min(1920, value));
|
||||
}
|
||||
|
||||
public int ResolutionHeight
|
||||
{
|
||||
get => _resolutionHeight;
|
||||
set => _resolutionHeight = Math.Max(240, Math.Min(1080, value));
|
||||
|
||||
public int ResolutionHeight
|
||||
{
|
||||
get => _resolutionHeight;
|
||||
set => _resolutionHeight = Math.Max(240, Math.Min(1080, value));
|
||||
}
|
||||
|
||||
public CameraService()
|
||||
@@ -75,7 +75,7 @@ namespace Ink_Canvas.Helpers
|
||||
{
|
||||
AvailableCameras.Clear();
|
||||
var videoDevices = new FilterInfoCollection(FilterCategory.VideoInputDevice);
|
||||
|
||||
|
||||
foreach (FilterInfo device in videoDevices)
|
||||
{
|
||||
AvailableCameras.Add(device);
|
||||
@@ -265,27 +265,27 @@ namespace Ink_Canvas.Helpers
|
||||
{
|
||||
// 释放之前的帧
|
||||
_currentFrame?.Dispose();
|
||||
|
||||
|
||||
// 创建新的位图,避免Clone的问题
|
||||
var sourceFrame = eventArgs.Frame;
|
||||
|
||||
|
||||
if (sourceFrame != null)
|
||||
{
|
||||
try
|
||||
{
|
||||
var width = sourceFrame.Width;
|
||||
var height = sourceFrame.Height;
|
||||
|
||||
if (width > 0 && height > 0)
|
||||
{
|
||||
// 应用旋转
|
||||
Bitmap rotatedFrame = ApplyRotation(sourceFrame);
|
||||
|
||||
// 应用分辨率调整
|
||||
_currentFrame = ResizeImage(rotatedFrame, _resolutionWidth, _resolutionHeight);
|
||||
|
||||
rotatedFrame?.Dispose();
|
||||
}
|
||||
|
||||
if (width > 0 && height > 0)
|
||||
{
|
||||
// 应用旋转
|
||||
Bitmap rotatedFrame = ApplyRotation(sourceFrame);
|
||||
|
||||
// 应用分辨率调整
|
||||
_currentFrame = ResizeImage(rotatedFrame, _resolutionWidth, _resolutionHeight);
|
||||
|
||||
rotatedFrame?.Dispose();
|
||||
}
|
||||
else
|
||||
{
|
||||
_currentFrame = null;
|
||||
@@ -379,7 +379,7 @@ namespace Ink_Canvas.Helpers
|
||||
public void Dispose()
|
||||
{
|
||||
StopPreview();
|
||||
|
||||
|
||||
lock (_frameLock)
|
||||
{
|
||||
_currentFrame?.Dispose();
|
||||
|
||||
@@ -419,7 +419,7 @@ namespace Ink_Canvas.Helpers
|
||||
try
|
||||
{
|
||||
string tempDir = Path.GetTempPath();
|
||||
|
||||
|
||||
// 处理文件路径IPC文件
|
||||
string[] ipcFiles = Directory.GetFiles(tempDir, IpcFilePrefix + "*.tmp");
|
||||
foreach (string ipcFile in ipcFiles)
|
||||
|
||||
@@ -242,7 +242,7 @@ namespace Ink_Canvas.Helpers
|
||||
public string Description { get; set; }
|
||||
public InterceptType? ParentType { get; set; }
|
||||
public List<InterceptType> ChildTypes { get; set; } = new List<InterceptType>();
|
||||
|
||||
|
||||
// 新增的精确匹配字段
|
||||
public bool HasWindowStyle { get; set; }
|
||||
public uint WindowStyle { get; set; }
|
||||
@@ -251,7 +251,7 @@ namespace Ink_Canvas.Helpers
|
||||
public int WindowHeight { get; set; }
|
||||
public bool ExactTitleMatch { get; set; } = false;
|
||||
public bool ExactClassNameMatch { get; set; } = false;
|
||||
|
||||
|
||||
// 运行时状态字段
|
||||
public bool foundHwnd { get; set; } = false;
|
||||
public IntPtr outHwnd { get; set; } = IntPtr.Zero;
|
||||
@@ -267,7 +267,7 @@ namespace Ink_Canvas.Helpers
|
||||
private readonly Dispatcher _dispatcher;
|
||||
private bool _isRunning;
|
||||
private bool _disposed;
|
||||
|
||||
|
||||
// 简化的性能统计
|
||||
private int _consecutiveEmptyScans = 0;
|
||||
private DateTime _lastSuccessfulScan = DateTime.Now;
|
||||
@@ -466,15 +466,15 @@ namespace Ink_Canvas.Helpers
|
||||
RequiresAdmin = true,
|
||||
Description = "畅言智慧课堂 主栏悬浮窗",
|
||||
ParentType = null,
|
||||
ChildTypes = new List<InterceptType>
|
||||
{
|
||||
InterceptType.ChangYanBrushSettings,
|
||||
InterceptType.ChangYanSwipeClear,
|
||||
InterceptType.ChangYanInteraction,
|
||||
InterceptType.ChangYanSubjectApp,
|
||||
InterceptType.ChangYanControl,
|
||||
InterceptType.ChangYanCommonTools,
|
||||
InterceptType.ChangYanSceneToolbar,
|
||||
ChildTypes = new List<InterceptType>
|
||||
{
|
||||
InterceptType.ChangYanBrushSettings,
|
||||
InterceptType.ChangYanSwipeClear,
|
||||
InterceptType.ChangYanInteraction,
|
||||
InterceptType.ChangYanSubjectApp,
|
||||
InterceptType.ChangYanControl,
|
||||
InterceptType.ChangYanCommonTools,
|
||||
InterceptType.ChangYanSceneToolbar,
|
||||
InterceptType.ChangYanDrawWindow
|
||||
}
|
||||
};
|
||||
@@ -713,7 +713,7 @@ namespace Ink_Canvas.Helpers
|
||||
if (_isRunning) return;
|
||||
|
||||
_isRunning = true;
|
||||
_scanTimer.Change(0, Math.Max(scanIntervalMs, 2000));
|
||||
_scanTimer.Change(0, Math.Max(scanIntervalMs, 2000));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -725,7 +725,7 @@ namespace Ink_Canvas.Helpers
|
||||
|
||||
_isRunning = false;
|
||||
_scanTimer.Change(Timeout.Infinite, Timeout.Infinite);
|
||||
|
||||
|
||||
// 恢复所有被拦截的窗口
|
||||
RestoreAllWindows();
|
||||
}
|
||||
@@ -774,9 +774,9 @@ namespace Ink_Canvas.Helpers
|
||||
{
|
||||
var parentRule = _interceptRules[rule.ParentType.Value];
|
||||
// 检查是否还有其他启用的子规则
|
||||
bool hasEnabledChildren = parentRule.ChildTypes.Any(childType =>
|
||||
bool hasEnabledChildren = parentRule.ChildTypes.Any(childType =>
|
||||
_interceptRules.ContainsKey(childType) && _interceptRules[childType].IsEnabled);
|
||||
|
||||
|
||||
// 如果没有启用的子规则,则禁用父规则
|
||||
if (!hasEnabledChildren)
|
||||
{
|
||||
@@ -831,7 +831,7 @@ namespace Ink_Canvas.Helpers
|
||||
{
|
||||
var windowsToRestore = new List<IntPtr>(_interceptedWindows.Keys);
|
||||
var restoredCount = 0;
|
||||
|
||||
|
||||
foreach (var hWnd in windowsToRestore)
|
||||
{
|
||||
if (RestoreWindow(hWnd))
|
||||
@@ -839,7 +839,7 @@ namespace Ink_Canvas.Helpers
|
||||
restoredCount++;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -864,7 +864,7 @@ namespace Ink_Canvas.Helpers
|
||||
restoredCount++;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -875,22 +875,22 @@ namespace Ink_Canvas.Helpers
|
||||
if (!_interceptedWindows.ContainsKey(hWnd)) return false;
|
||||
|
||||
var interceptType = _interceptedWindows[hWnd];
|
||||
|
||||
|
||||
if (IsWindow(hWnd))
|
||||
{
|
||||
// 使用多种方法确保窗口恢复显示
|
||||
ShowWindow(hWnd, SW_RESTORE);
|
||||
ShowWindow(hWnd, SW_SHOW);
|
||||
ShowWindow(hWnd, SW_SHOWNORMAL);
|
||||
|
||||
|
||||
// 将窗口置于前台并显示
|
||||
SetWindowPos(hWnd, IntPtr.Zero, 0, 0, 0, 0,
|
||||
SetWindowPos(hWnd, IntPtr.Zero, 0, 0, 0, 0,
|
||||
SWP_NOMOVE | SWP_NOSIZE | SWP_NOZORDER | SWP_SHOWWINDOW);
|
||||
|
||||
|
||||
// 强制将窗口带到前台
|
||||
BringWindowToTop(hWnd);
|
||||
SetForegroundWindow(hWnd);
|
||||
|
||||
|
||||
_interceptedWindows.Remove(hWnd);
|
||||
|
||||
WindowRestored?.Invoke(this, new WindowRestoredEventArgs
|
||||
@@ -916,7 +916,7 @@ namespace Ink_Canvas.Helpers
|
||||
private void CleanupInvalidWindows()
|
||||
{
|
||||
var invalidWindows = new List<IntPtr>();
|
||||
|
||||
|
||||
foreach (var kvp in _interceptedWindows)
|
||||
{
|
||||
var hWnd = kvp.Key;
|
||||
@@ -940,7 +940,7 @@ namespace Ink_Canvas.Helpers
|
||||
// 简化的扫描逻辑
|
||||
var interceptedCount = 0;
|
||||
CleanupInvalidWindows();
|
||||
|
||||
|
||||
// 重置所有规则的发现状态
|
||||
foreach (var rule in _interceptRules.Values)
|
||||
{
|
||||
@@ -958,9 +958,9 @@ namespace Ink_Canvas.Helpers
|
||||
{
|
||||
if (rule.IsEnabled && rule.foundHwnd && rule.outHwnd != IntPtr.Zero)
|
||||
{
|
||||
bool shouldIntercept = !_interceptedWindows.ContainsKey(rule.outHwnd) ||
|
||||
bool shouldIntercept = !_interceptedWindows.ContainsKey(rule.outHwnd) ||
|
||||
(_interceptedWindows.ContainsKey(rule.outHwnd) && IsWindowVisible(rule.outHwnd));
|
||||
|
||||
|
||||
if (shouldIntercept)
|
||||
{
|
||||
InterceptWindow(rule.outHwnd, rule);
|
||||
@@ -1068,7 +1068,7 @@ namespace Ink_Canvas.Helpers
|
||||
var className = new StringBuilder(256);
|
||||
GetClassName(hWnd, className, className.Capacity);
|
||||
var classNameStr = className.ToString();
|
||||
|
||||
|
||||
if (rule.ExactClassNameMatch)
|
||||
{
|
||||
if (!classNameStr.Equals(rule.ClassNamePattern, StringComparison.OrdinalIgnoreCase))
|
||||
@@ -1087,7 +1087,7 @@ namespace Ink_Canvas.Helpers
|
||||
var windowTitle = new StringBuilder(256);
|
||||
GetWindowText(hWnd, windowTitle, windowTitle.Capacity);
|
||||
var titleStr = windowTitle.ToString();
|
||||
|
||||
|
||||
if (rule.ExactTitleMatch)
|
||||
{
|
||||
if (!titleStr.Equals(rule.WindowTitlePattern, StringComparison.OrdinalIgnoreCase))
|
||||
@@ -1126,7 +1126,7 @@ namespace Ink_Canvas.Helpers
|
||||
var horizontalDPI = GetDeviceCaps(hdc, LOGPIXELSX);
|
||||
var verticalDPI = GetDeviceCaps(hdc, LOGPIXELSY);
|
||||
ReleaseDC(IntPtr.Zero, hdc);
|
||||
|
||||
|
||||
var scale = (horizontalDPI + verticalDPI) / 2.0f / 96.0f;
|
||||
var scaledWidth = (int)(rule.WindowWidth * scale);
|
||||
var scaledHeight = (int)(rule.WindowHeight * scale);
|
||||
@@ -1164,10 +1164,10 @@ namespace Ink_Canvas.Helpers
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
// 直接隐藏窗口,不发送关闭消息
|
||||
ShowWindow(hWnd, SW_HIDE);
|
||||
|
||||
|
||||
// 记录拦截的窗口
|
||||
_interceptedWindows[hWnd] = rule.Type;
|
||||
|
||||
|
||||
@@ -6,8 +6,8 @@ using System.IO;
|
||||
using System.Reflection;
|
||||
using System.Text;
|
||||
using System.Windows;
|
||||
using System.Windows.Input;
|
||||
using System.Windows.Forms;
|
||||
using System.Windows.Input;
|
||||
|
||||
namespace Ink_Canvas.Helpers
|
||||
{
|
||||
@@ -21,12 +21,12 @@ namespace Ink_Canvas.Helpers
|
||||
private readonly MainWindow _mainWindow;
|
||||
private bool _isDisposed;
|
||||
private bool _hotkeysShouldBeRegistered = true; // 启动时注册热键
|
||||
|
||||
|
||||
// 多屏幕支持相关字段
|
||||
private Screen _currentScreen;
|
||||
private bool _isMultiScreenMode = false;
|
||||
private bool _enableScreenSpecificHotkeys = true; // 是否启用基于屏幕的热键注册
|
||||
|
||||
|
||||
// 智能热键管理相关字段
|
||||
private bool _isWindowFocused = false;
|
||||
private bool _isMouseOverWindow = false;
|
||||
@@ -42,10 +42,10 @@ namespace Ink_Canvas.Helpers
|
||||
_mainWindow = mainWindow ?? throw new ArgumentNullException(nameof(mainWindow));
|
||||
_registeredHotkeys = new Dictionary<string, HotkeyInfo>();
|
||||
_hotkeysShouldBeRegistered = true; // 启动时注册热键
|
||||
|
||||
|
||||
// 初始化多屏幕支持
|
||||
InitializeMultiScreenSupport();
|
||||
|
||||
|
||||
// 启动时确保配置文件存在
|
||||
EnsureConfigFileExists();
|
||||
}
|
||||
@@ -106,10 +106,10 @@ namespace Ink_Canvas.Helpers
|
||||
});
|
||||
|
||||
_registeredHotkeys[hotkeyName] = hotkeyInfo;
|
||||
|
||||
|
||||
// 记录注册信息
|
||||
var screenInfo = _isMultiScreenMode ? $" (屏幕: {_currentScreen?.DeviceName})" : "";
|
||||
|
||||
|
||||
return true;
|
||||
}
|
||||
catch (Exception ex)
|
||||
@@ -506,7 +506,7 @@ namespace Ink_Canvas.Helpers
|
||||
try
|
||||
{
|
||||
_enableScreenSpecificHotkeys = true;
|
||||
|
||||
|
||||
// 如果当前在多屏幕环境下,刷新热键注册
|
||||
if (_isMultiScreenMode)
|
||||
{
|
||||
@@ -527,7 +527,7 @@ namespace Ink_Canvas.Helpers
|
||||
try
|
||||
{
|
||||
_enableScreenSpecificHotkeys = false;
|
||||
|
||||
|
||||
// 重新注册热键(全局模式)
|
||||
if (_hotkeysShouldBeRegistered)
|
||||
{
|
||||
@@ -599,15 +599,15 @@ namespace Ink_Canvas.Helpers
|
||||
{
|
||||
// 检测是否有多个屏幕
|
||||
_isMultiScreenMode = ScreenDetectionHelper.HasMultipleScreens();
|
||||
|
||||
|
||||
if (_isMultiScreenMode)
|
||||
{
|
||||
// 获取当前窗口所在的屏幕
|
||||
_currentScreen = ScreenDetectionHelper.GetWindowScreen(_mainWindow);
|
||||
|
||||
|
||||
// 监听窗口位置变化事件
|
||||
_mainWindow.LocationChanged += OnWindowLocationChanged;
|
||||
|
||||
|
||||
// 初始化智能热键管理
|
||||
InitializeSmartHotkeyManagement();
|
||||
}
|
||||
@@ -634,16 +634,16 @@ namespace Ink_Canvas.Helpers
|
||||
// 监听窗口焦点事件
|
||||
_mainWindow.GotFocus += OnWindowGotFocus;
|
||||
_mainWindow.LostFocus += OnWindowLostFocus;
|
||||
|
||||
|
||||
// 监听鼠标进入/离开事件
|
||||
_mainWindow.MouseEnter += OnMouseEnterWindow;
|
||||
_mainWindow.MouseLeave += OnMouseLeaveWindow;
|
||||
|
||||
|
||||
// 初始化鼠标位置监控定时器
|
||||
_mousePositionTimer = new System.Windows.Threading.DispatcherTimer();
|
||||
_mousePositionTimer.Interval = TimeSpan.FromMilliseconds(500); // 每500ms检查一次
|
||||
_mousePositionTimer.Tick += OnMousePositionTimerTick;
|
||||
|
||||
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
@@ -665,7 +665,7 @@ namespace Ink_Canvas.Helpers
|
||||
if (newScreen != null && newScreen != _currentScreen)
|
||||
{
|
||||
_currentScreen = newScreen;
|
||||
|
||||
|
||||
// 重新注册热键以适应新屏幕
|
||||
RefreshHotkeysForCurrentScreen();
|
||||
}
|
||||
@@ -691,7 +691,7 @@ namespace Ink_Canvas.Helpers
|
||||
|
||||
// 重新注册热键
|
||||
LoadHotkeysFromSettings();
|
||||
|
||||
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
@@ -776,12 +776,12 @@ namespace Ink_Canvas.Helpers
|
||||
// 检查鼠标是否在当前窗口所在的屏幕上
|
||||
var mousePosition = Control.MousePosition;
|
||||
var currentScreen = Screen.FromPoint(mousePosition);
|
||||
|
||||
|
||||
// 无论屏幕是否变化,都检查热键状态
|
||||
// 这样可以确保热键状态始终与当前上下文保持一致
|
||||
bool shouldEnableHotkeys = ShouldEnableHotkeysBasedOnContext();
|
||||
bool currentlyHasHotkeys = _registeredHotkeys.Count > 0;
|
||||
|
||||
|
||||
if (shouldEnableHotkeys && !currentlyHasHotkeys)
|
||||
{
|
||||
UpdateHotkeyStateBasedOnContext();
|
||||
@@ -808,7 +808,7 @@ namespace Ink_Canvas.Helpers
|
||||
return;
|
||||
|
||||
bool shouldEnableHotkeys = ShouldEnableHotkeysBasedOnContext();
|
||||
|
||||
|
||||
if (shouldEnableHotkeys)
|
||||
{
|
||||
// 如果热键未注册,则注册
|
||||
@@ -823,7 +823,7 @@ namespace Ink_Canvas.Helpers
|
||||
if (_registeredHotkeys.Count > 0)
|
||||
{
|
||||
UnregisterAllHotkeys();
|
||||
|
||||
|
||||
// 注意:这里不设置 _hotkeysShouldBeRegistered = false
|
||||
// 因为我们需要保持热键系统的启用状态,只是暂时注销热键
|
||||
// 这样当上下文变化时,热键可以重新注册
|
||||
@@ -882,7 +882,7 @@ namespace Ink_Canvas.Helpers
|
||||
{
|
||||
var mousePosition = Control.MousePosition;
|
||||
var mouseScreen = Screen.FromPoint(mousePosition);
|
||||
|
||||
|
||||
if (mouseScreen == _currentScreen)
|
||||
{
|
||||
return true;
|
||||
@@ -1344,14 +1344,14 @@ namespace Ink_Canvas.Helpers
|
||||
{
|
||||
// 注销所有快捷键
|
||||
UnregisterAllHotkeys();
|
||||
|
||||
|
||||
// 停止定时器
|
||||
if (_mousePositionTimer != null)
|
||||
{
|
||||
_mousePositionTimer.Stop();
|
||||
_mousePositionTimer = null;
|
||||
}
|
||||
|
||||
|
||||
// 移除事件监听器
|
||||
if (_mainWindow != null)
|
||||
{
|
||||
@@ -1359,7 +1359,7 @@ namespace Ink_Canvas.Helpers
|
||||
{
|
||||
_mainWindow.LocationChanged -= OnWindowLocationChanged;
|
||||
}
|
||||
|
||||
|
||||
_mainWindow.GotFocus -= OnWindowGotFocus;
|
||||
_mainWindow.LostFocus -= OnWindowLostFocus;
|
||||
_mainWindow.MouseEnter -= OnMouseEnterWindow;
|
||||
|
||||
@@ -77,40 +77,40 @@ namespace Ink_Canvas.Helpers
|
||||
{
|
||||
// 保存用户设置的异步处理偏好
|
||||
bool userAsyncPreference = UseAsyncProcessing;
|
||||
|
||||
|
||||
switch (Quality)
|
||||
{
|
||||
case SmoothingQuality.Performance:
|
||||
SmoothingStrength = 0.15;
|
||||
ResampleInterval = 5.0;
|
||||
InterpolationSteps = 4;
|
||||
SmoothingStrength = 0.15;
|
||||
ResampleInterval = 5.0;
|
||||
InterpolationSteps = 4;
|
||||
UseAdaptiveInterpolation = false;
|
||||
CurveTension = 0.15;
|
||||
CurveTension = 0.15;
|
||||
MaxConcurrentTasks = Math.Max(1, Environment.ProcessorCount / 2);
|
||||
UseHardwareAcceleration = true;
|
||||
UseAsyncProcessing = userAsyncPreference;
|
||||
UseHardwareAcceleration = true;
|
||||
UseAsyncProcessing = userAsyncPreference;
|
||||
break;
|
||||
|
||||
case SmoothingQuality.Balanced:
|
||||
SmoothingStrength = 0.3;
|
||||
ResampleInterval = 3.0;
|
||||
InterpolationSteps = 8;
|
||||
SmoothingStrength = 0.3;
|
||||
ResampleInterval = 3.0;
|
||||
InterpolationSteps = 8;
|
||||
UseAdaptiveInterpolation = true;
|
||||
CurveTension = 0.25;
|
||||
CurveTension = 0.25;
|
||||
MaxConcurrentTasks = Environment.ProcessorCount;
|
||||
UseHardwareAcceleration = true;
|
||||
UseAsyncProcessing = userAsyncPreference;
|
||||
UseAsyncProcessing = userAsyncPreference;
|
||||
break;
|
||||
|
||||
case SmoothingQuality.Quality:
|
||||
SmoothingStrength = 0.5;
|
||||
ResampleInterval = 2.0;
|
||||
InterpolationSteps = 15;
|
||||
SmoothingStrength = 0.5;
|
||||
ResampleInterval = 2.0;
|
||||
InterpolationSteps = 15;
|
||||
UseAdaptiveInterpolation = true;
|
||||
CurveTension = 0.35;
|
||||
CurveTension = 0.35;
|
||||
MaxConcurrentTasks = Environment.ProcessorCount;
|
||||
UseHardwareAcceleration = true;
|
||||
UseAsyncProcessing = userAsyncPreference;
|
||||
UseAsyncProcessing = userAsyncPreference;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -26,7 +26,7 @@ namespace Ink_Canvas.Helpers
|
||||
private readonly object _lockObject = new object();
|
||||
private bool _disposed;
|
||||
private string _currentActivePresentationId = "";
|
||||
|
||||
|
||||
// 墨迹备份机制
|
||||
private readonly Dictionary<string, Dictionary<int, StrokeCollection>> _strokeBackups;
|
||||
private DateTime _lastBackupTime = DateTime.MinValue;
|
||||
@@ -55,7 +55,7 @@ namespace Ink_Canvas.Helpers
|
||||
try
|
||||
{
|
||||
var presentationId = GeneratePresentationId(presentation);
|
||||
|
||||
|
||||
// 如果已存在该演示文稿的管理器,先清理
|
||||
if (_presentationManagers.ContainsKey(presentationId))
|
||||
{
|
||||
@@ -104,11 +104,11 @@ namespace Ink_Canvas.Helpers
|
||||
try
|
||||
{
|
||||
var presentationId = GeneratePresentationId(presentation);
|
||||
|
||||
|
||||
if (_presentationManagers.ContainsKey(presentationId))
|
||||
{
|
||||
// 如果切换的是不同的演示文稿,先保存当前活跃演示文稿的墨迹
|
||||
if (!string.IsNullOrEmpty(_currentActivePresentationId) &&
|
||||
if (!string.IsNullOrEmpty(_currentActivePresentationId) &&
|
||||
_currentActivePresentationId != presentationId)
|
||||
{
|
||||
var currentManager = GetCurrentManager();
|
||||
@@ -132,7 +132,7 @@ namespace Ink_Canvas.Helpers
|
||||
}
|
||||
|
||||
_currentActivePresentationId = presentationId;
|
||||
|
||||
|
||||
// 更新最后访问时间
|
||||
if (_presentationInfos.ContainsKey(presentationId))
|
||||
{
|
||||
@@ -176,13 +176,13 @@ namespace Ink_Canvas.Helpers
|
||||
{
|
||||
// 保存到管理器
|
||||
manager.SaveCurrentSlideStrokes(slideIndex, strokes);
|
||||
|
||||
|
||||
// 只有在保存成功后才创建备份
|
||||
if (!string.IsNullOrEmpty(_currentActivePresentationId))
|
||||
{
|
||||
CreateStrokeBackup(_currentActivePresentationId, slideIndex, strokes);
|
||||
}
|
||||
|
||||
|
||||
// 检查是否需要执行定期备份
|
||||
CheckAndPerformBackup();
|
||||
}
|
||||
@@ -233,7 +233,7 @@ namespace Ink_Canvas.Helpers
|
||||
if (manager != null)
|
||||
{
|
||||
var strokes = manager.LoadSlideStrokes(slideIndex);
|
||||
|
||||
|
||||
// 如果从管理器加载失败,尝试从备份恢复
|
||||
if (strokes == null || strokes.Count == 0)
|
||||
{
|
||||
@@ -242,14 +242,14 @@ namespace Ink_Canvas.Helpers
|
||||
strokes = RestoreStrokeFromBackup(_currentActivePresentationId, slideIndex);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
return strokes ?? new StrokeCollection();
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
LogHelper.WriteLogToFile($"加载页面墨迹失败: {ex}", LogHelper.LogType.Error);
|
||||
|
||||
|
||||
// 尝试从备份恢复
|
||||
if (!string.IsNullOrEmpty(_currentActivePresentationId))
|
||||
{
|
||||
@@ -464,12 +464,12 @@ namespace Ink_Canvas.Helpers
|
||||
try
|
||||
{
|
||||
var presentationId = GeneratePresentationId(presentation);
|
||||
|
||||
|
||||
if (_presentationManagers.ContainsKey(presentationId))
|
||||
{
|
||||
// 保存墨迹到文件
|
||||
_presentationManagers[presentationId].SaveAllStrokesToFile(presentation);
|
||||
|
||||
|
||||
// 释放资源
|
||||
_presentationManagers[presentationId].Dispose();
|
||||
_presentationManagers.Remove(presentationId);
|
||||
@@ -550,13 +550,13 @@ namespace Ink_Canvas.Helpers
|
||||
_presentationManagers.Remove(id);
|
||||
}
|
||||
_presentationInfos.Remove(id);
|
||||
|
||||
|
||||
// 清理备份数据
|
||||
if (_strokeBackups.ContainsKey(id))
|
||||
{
|
||||
_strokeBackups.Remove(id);
|
||||
}
|
||||
|
||||
|
||||
LogHelper.WriteLogToFile($"已清理非活跃演示文稿: {id}", LogHelper.LogType.Trace);
|
||||
}
|
||||
}
|
||||
@@ -589,7 +589,7 @@ namespace Ink_Canvas.Helpers
|
||||
|
||||
// 创建新的备份
|
||||
_strokeBackups[presentationId][slideIndex] = strokes.Clone();
|
||||
|
||||
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
@@ -604,7 +604,7 @@ namespace Ink_Canvas.Helpers
|
||||
{
|
||||
try
|
||||
{
|
||||
if (_strokeBackups.ContainsKey(presentationId) &&
|
||||
if (_strokeBackups.ContainsKey(presentationId) &&
|
||||
_strokeBackups[presentationId].ContainsKey(slideIndex))
|
||||
{
|
||||
var backup = _strokeBackups[presentationId][slideIndex];
|
||||
@@ -631,7 +631,7 @@ namespace Ink_Canvas.Helpers
|
||||
try
|
||||
{
|
||||
var now = DateTime.Now;
|
||||
|
||||
|
||||
// 检查是否需要执行备份
|
||||
if (now - _lastBackupTime < TimeSpan.FromMinutes(BackupIntervalMinutes))
|
||||
{
|
||||
@@ -639,7 +639,7 @@ namespace Ink_Canvas.Helpers
|
||||
}
|
||||
|
||||
// 备份当前活跃演示文稿的所有墨迹
|
||||
if (!string.IsNullOrEmpty(_currentActivePresentationId) &&
|
||||
if (!string.IsNullOrEmpty(_currentActivePresentationId) &&
|
||||
_presentationManagers.ContainsKey(_currentActivePresentationId))
|
||||
{
|
||||
var manager = _presentationManagers[_currentActivePresentationId];
|
||||
@@ -661,7 +661,7 @@ namespace Ink_Canvas.Helpers
|
||||
#region Private Methods
|
||||
private PPTInkManager GetCurrentManager()
|
||||
{
|
||||
if (string.IsNullOrEmpty(_currentActivePresentationId) ||
|
||||
if (string.IsNullOrEmpty(_currentActivePresentationId) ||
|
||||
!_presentationManagers.ContainsKey(_currentActivePresentationId))
|
||||
{
|
||||
return null;
|
||||
@@ -780,7 +780,7 @@ namespace Ink_Canvas.Helpers
|
||||
}
|
||||
_presentationManagers.Clear();
|
||||
_presentationInfos.Clear();
|
||||
|
||||
|
||||
// 清理备份数据
|
||||
foreach (var backupDict in _strokeBackups.Values)
|
||||
{
|
||||
|
||||
@@ -31,7 +31,7 @@ namespace Ink_Canvas.Helpers
|
||||
{
|
||||
private bool _needsRedraw = true;
|
||||
private int _lastPointCount = 0;
|
||||
private const int REDRAW_THRESHOLD = 3;
|
||||
private const int REDRAW_THRESHOLD = 3;
|
||||
|
||||
/// <summary>
|
||||
/// 创建显示笔迹的类
|
||||
@@ -53,7 +53,7 @@ namespace Ink_Canvas.Helpers
|
||||
public StrokeVisual(DrawingAttributes drawingAttributes)
|
||||
{
|
||||
_drawingAttributes = drawingAttributes;
|
||||
|
||||
|
||||
// 启用硬件加速
|
||||
RenderOptions.SetBitmapScalingMode(this, BitmapScalingMode.HighQuality);
|
||||
RenderOptions.SetEdgeMode(this, EdgeMode.Aliased);
|
||||
@@ -82,7 +82,7 @@ namespace Ink_Canvas.Helpers
|
||||
Stroke.StylusPoints.Add(point);
|
||||
_lastPointCount++;
|
||||
}
|
||||
|
||||
|
||||
// 标记需要重绘
|
||||
_needsRedraw = true;
|
||||
}
|
||||
@@ -93,7 +93,7 @@ namespace Ink_Canvas.Helpers
|
||||
public void Redraw()
|
||||
{
|
||||
if (!_needsRedraw || Stroke == null) return;
|
||||
|
||||
|
||||
if (_lastPointCount % REDRAW_THRESHOLD != 0 && _lastPointCount > REDRAW_THRESHOLD)
|
||||
{
|
||||
return;
|
||||
|
||||
@@ -30,12 +30,12 @@ namespace Ink_Canvas.Helpers
|
||||
private DateTime _inkLockUntil = DateTime.MinValue;
|
||||
private int _lockedSlideIndex = -1;
|
||||
private const int InkLockMilliseconds = 500;
|
||||
|
||||
|
||||
// 添加快速切换保护机制
|
||||
private DateTime _lastSwitchTime = DateTime.MinValue;
|
||||
private int _lastSwitchSlideIndex = -1;
|
||||
private const int MinSwitchIntervalMs = 100; // 最小切换间隔100毫秒
|
||||
|
||||
|
||||
// 内存管理相关字段
|
||||
private long _totalMemoryUsage = 0;
|
||||
private const long MaxMemoryUsageBytes = 100 * 1024 * 1024; // 100MB限制
|
||||
@@ -90,7 +90,7 @@ namespace Ink_Canvas.Helpers
|
||||
{
|
||||
return;
|
||||
}
|
||||
throw;
|
||||
throw;
|
||||
}
|
||||
_memoryStreams = new MemoryStream[slideCount + 2];
|
||||
|
||||
@@ -238,7 +238,7 @@ namespace Ink_Canvas.Helpers
|
||||
{
|
||||
// 检查快速切换保护
|
||||
var now = DateTime.Now;
|
||||
if (now - _lastSwitchTime < TimeSpan.FromMilliseconds(MinSwitchIntervalMs) &&
|
||||
if (now - _lastSwitchTime < TimeSpan.FromMilliseconds(MinSwitchIntervalMs) &&
|
||||
_lastSwitchSlideIndex == slideIndex)
|
||||
{
|
||||
LogHelper.WriteLogToFile($"快速切换保护:忽略重复的页面切换请求 {slideIndex}", LogHelper.LogType.Warning);
|
||||
@@ -251,11 +251,11 @@ namespace Ink_Canvas.Helpers
|
||||
|
||||
// 加载新页面的墨迹
|
||||
var newStrokes = LoadSlideStrokes(slideIndex);
|
||||
|
||||
|
||||
// 更新切换记录
|
||||
_lastSwitchTime = now;
|
||||
_lastSwitchSlideIndex = slideIndex;
|
||||
|
||||
|
||||
if (newStrokes.Count > 0)
|
||||
{
|
||||
}
|
||||
@@ -300,7 +300,7 @@ namespace Ink_Canvas.Helpers
|
||||
// 保存所有页面的墨迹
|
||||
int savedCount = 0;
|
||||
int slideCount = 0;
|
||||
|
||||
|
||||
try
|
||||
{
|
||||
slideCount = presentation.Slides.Count;
|
||||
@@ -308,13 +308,13 @@ namespace Ink_Canvas.Helpers
|
||||
catch (COMException comEx)
|
||||
{
|
||||
var hr = (uint)comEx.HResult;
|
||||
if (hr == 0x80048010)
|
||||
if (hr == 0x80048010)
|
||||
{
|
||||
return;
|
||||
}
|
||||
throw;
|
||||
throw;
|
||||
}
|
||||
|
||||
|
||||
for (int i = 1; i <= slideCount && i < _memoryStreams.Length; i++)
|
||||
{
|
||||
if (_memoryStreams[i] != null)
|
||||
@@ -430,7 +430,7 @@ namespace Ink_Canvas.Helpers
|
||||
_memoryStreams[i] = null;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// 重新初始化数组
|
||||
_memoryStreams = new MemoryStream[_maxSlides + 2];
|
||||
}
|
||||
@@ -464,20 +464,20 @@ namespace Ink_Canvas.Helpers
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
// 如果当前页面与锁定页面相同,允许写入(用户在当前页面绘制)
|
||||
if (currentSlideIndex == _lockedSlideIndex)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
// 如果当前页面不是锁定页面,但锁定时间很短(小于50ms),允许写入
|
||||
// 这样可以确保旧页面的墨迹能够及时保存
|
||||
if (DateTime.Now - (_inkLockUntil.AddMilliseconds(-InkLockMilliseconds)) < TimeSpan.FromMilliseconds(50))
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
// 只有在快速切换且页面不同时才锁定
|
||||
return false;
|
||||
}
|
||||
@@ -504,7 +504,7 @@ namespace Ink_Canvas.Helpers
|
||||
try
|
||||
{
|
||||
var now = DateTime.Now;
|
||||
|
||||
|
||||
// 检查是否需要执行内存清理
|
||||
if (now - _lastMemoryCleanup < TimeSpan.FromMinutes(MemoryCleanupIntervalMinutes))
|
||||
{
|
||||
@@ -530,10 +530,10 @@ namespace Ink_Canvas.Helpers
|
||||
if (currentMemoryUsage > MaxMemoryUsageBytes)
|
||||
{
|
||||
LogHelper.WriteLogToFile($"内存使用量超限 ({currentMemoryUsage / 1024 / 1024}MB),开始清理", LogHelper.LogType.Warning);
|
||||
|
||||
|
||||
// 清理非当前页面的墨迹
|
||||
CleanupInactiveSlideStrokes();
|
||||
|
||||
|
||||
_lastMemoryCleanup = now;
|
||||
LogHelper.WriteLogToFile($"内存清理完成,当前使用量: {_totalMemoryUsage / 1024 / 1024}MB", LogHelper.LogType.Trace);
|
||||
}
|
||||
@@ -571,7 +571,7 @@ namespace Ink_Canvas.Helpers
|
||||
if (_memoryStreams[i] != null)
|
||||
{
|
||||
long memorySize = _memoryStreams[i].Length;
|
||||
|
||||
|
||||
try
|
||||
{
|
||||
_memoryStreams[i].Dispose();
|
||||
|
||||
@@ -104,8 +104,8 @@ namespace Ink_Canvas.Helpers
|
||||
_dispatcher.BeginInvoke(new Action(() =>
|
||||
{
|
||||
MainWindow.MoveWindow(new WindowInteropHelper(_mainWindow).Handle, 0, 0,
|
||||
System.Windows.Forms.Screen.PrimaryScreen.Bounds.Width,
|
||||
System.Windows.Forms.Screen.PrimaryScreen.Bounds.Height, true);
|
||||
System.Windows.Forms.Screen.PrimaryScreen.Bounds.Width,
|
||||
System.Windows.Forms.Screen.PrimaryScreen.Bounds.Height, true);
|
||||
}), DispatcherPriority.ApplicationIdle);
|
||||
}
|
||||
}
|
||||
@@ -118,12 +118,12 @@ namespace Ink_Canvas.Helpers
|
||||
{
|
||||
// 恢复为非画板模式,重新启用全屏限制
|
||||
AvoidFullScreenHelper.SetBoardMode(false);
|
||||
|
||||
|
||||
_dispatcher.BeginInvoke(new Action(() =>
|
||||
{
|
||||
// 退出PPT放映模式,恢复到工作区域大小
|
||||
var workingArea = System.Windows.Forms.Screen.PrimaryScreen.WorkingArea;
|
||||
MainWindow.MoveWindow(new WindowInteropHelper(_mainWindow).Handle,
|
||||
MainWindow.MoveWindow(new WindowInteropHelper(_mainWindow).Handle,
|
||||
workingArea.X, workingArea.Y,
|
||||
workingArea.Width, workingArea.Height, true);
|
||||
}), DispatcherPriority.ApplicationIdle);
|
||||
|
||||
@@ -31,7 +31,7 @@ namespace Ink_Canvas.Helpers
|
||||
|
||||
// 获取窗口在屏幕上的位置
|
||||
var windowRect = GetWindowScreenBounds(window);
|
||||
|
||||
|
||||
// 查找与窗口重叠最多的屏幕
|
||||
Screen targetScreen = null;
|
||||
double maxIntersection = 0;
|
||||
@@ -66,10 +66,10 @@ namespace Ink_Canvas.Helpers
|
||||
{
|
||||
// 获取窗口左上角在屏幕上的位置
|
||||
var topLeft = window.PointToScreen(new Point(0, 0));
|
||||
|
||||
|
||||
// 获取窗口右下角在屏幕上的位置
|
||||
var bottomRight = window.PointToScreen(new Point(window.ActualWidth, window.ActualHeight));
|
||||
|
||||
|
||||
return new Rectangle(
|
||||
(int)topLeft.X,
|
||||
(int)topLeft.Y,
|
||||
|
||||
Reference in New Issue
Block a user