diff --git a/InkCanvasForClass/App.xaml.cs b/InkCanvasForClass/App.xaml.cs
index 4cb2f65..cb01333 100644
--- a/InkCanvasForClass/App.xaml.cs
+++ b/InkCanvasForClass/App.xaml.cs
@@ -15,6 +15,8 @@ using Window = System.Windows.Window;
using System.Windows.Shell;
using Ookii.Dialogs.Wpf;
using System.Diagnostics;
+using Ink_Canvas.Popups;
+using Ink_Canvas.Windows;
using Lierda.WPFHelper;
namespace Ink_Canvas
@@ -115,6 +117,9 @@ namespace Ink_Canvas
}
mainWin.Show();
+ var setW = new SettingsWindow();
+ setW.Show();
+
_taskbar = (TaskbarIcon)FindResource("TaskbarTrayIcon");
LierdaCracker cracker = new LierdaCracker();
diff --git a/InkCanvasForClass/InkCanvasForClass.csproj b/InkCanvasForClass/InkCanvasForClass.csproj
index 10a855c..58955ad 100644
--- a/InkCanvasForClass/InkCanvasForClass.csproj
+++ b/InkCanvasForClass/InkCanvasForClass.csproj
@@ -25,6 +25,7 @@
False
true
Debug;Release;x86 Debug
+ false
embedded
@@ -597,6 +598,9 @@
PreserveNewest
+
+ Always
+
diff --git a/InkCanvasForClass/InkCanvasForClass.csproj.user b/InkCanvasForClass/InkCanvasForClass.csproj.user
index 403f6f0..9e6bd27 100644
--- a/InkCanvasForClass/InkCanvasForClass.csproj.user
+++ b/InkCanvasForClass/InkCanvasForClass.csproj.user
@@ -17,9 +17,6 @@
Code
-
- Code
-
Code
@@ -29,6 +26,9 @@
Code
+
+ Code
+
@@ -46,12 +46,6 @@
Designer
-
- Designer
-
-
- Designer
-
Designer
@@ -64,7 +58,7 @@
Designer
-
+
Designer
diff --git a/InkCanvasForClass/Popups/FloatingBarV2Resources.xaml b/InkCanvasForClass/Popups/FloatingBarV2Resources.xaml
deleted file mode 100644
index cc1bd18..0000000
--- a/InkCanvasForClass/Popups/FloatingBarV2Resources.xaml
+++ /dev/null
@@ -1,13 +0,0 @@
-
-
-
-
-
-
-
-
-
-
-
-
\ No newline at end of file
diff --git a/InkCanvasForClass/Popups/FloatingBarWindowV2.xaml b/InkCanvasForClass/Popups/FloatingBarWindowV2.xaml
deleted file mode 100644
index a5f0349..0000000
--- a/InkCanvasForClass/Popups/FloatingBarWindowV2.xaml
+++ /dev/null
@@ -1,90 +0,0 @@
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
diff --git a/InkCanvasForClass/Popups/FloatingBarWindowV2.xaml.cs b/InkCanvasForClass/Popups/FloatingBarWindowV2.xaml.cs
deleted file mode 100644
index 8bf2c2d..0000000
--- a/InkCanvasForClass/Popups/FloatingBarWindowV2.xaml.cs
+++ /dev/null
@@ -1,27 +0,0 @@
-using System;
-using System.Collections.Generic;
-using System.Linq;
-using System.Text;
-using System.Threading.Tasks;
-using System.Windows;
-using System.Windows.Controls;
-using System.Windows.Data;
-using System.Windows.Documents;
-using System.Windows.Input;
-using System.Windows.Media;
-using System.Windows.Media.Imaging;
-using System.Windows.Shapes;
-
-namespace Ink_Canvas.Popups
-{
- ///
- /// FloatingBarWindowV2.xaml 的交互逻辑
- ///
- public partial class FloatingBarWindowV2 : Window
- {
- public FloatingBarWindowV2()
- {
- InitializeComponent();
- }
- }
-}
diff --git a/InkCanvasForClass/Resources/Themes/DarkFloatingBarTheme.xaml b/InkCanvasForClass/Resources/Themes/DarkFloatingBarTheme.xaml
deleted file mode 100644
index a60cfa1..0000000
--- a/InkCanvasForClass/Resources/Themes/DarkFloatingBarTheme.xaml
+++ /dev/null
@@ -1,12 +0,0 @@
-
-
-
-
-
\ No newline at end of file
diff --git a/InkCanvasForClass/Windows/SettingsWindow.xaml b/InkCanvasForClass/Windows/SettingsWindow.xaml
new file mode 100644
index 0000000..321f282
--- /dev/null
+++ b/InkCanvasForClass/Windows/SettingsWindow.xaml
@@ -0,0 +1,330 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/InkCanvasForClass/Windows/SettingsWindow.xaml.cs b/InkCanvasForClass/Windows/SettingsWindow.xaml.cs
new file mode 100644
index 0000000..4b94524
--- /dev/null
+++ b/InkCanvasForClass/Windows/SettingsWindow.xaml.cs
@@ -0,0 +1,329 @@
+using System;
+using System.Collections.Generic;
+using System.Collections.ObjectModel;
+using System.IO;
+using System.Linq;
+using System.Management;
+using System.Reflection;
+using System.Runtime.InteropServices;
+using System.Text;
+using System.Threading;
+using System.Threading.Tasks;
+using System.Windows;
+using System.Windows.Controls;
+using System.Windows.Data;
+using System.Windows.Documents;
+using System.Windows.Input;
+using System.Windows.Media;
+using System.Windows.Media.Imaging;
+using System.Windows.Shapes;
+using iNKORE.UI.WPF.Helpers;
+using OSVersionExtension;
+
+namespace Ink_Canvas.Windows {
+ public partial class SettingsWindow : Window {
+
+ public SettingsWindow() {
+ InitializeComponent();
+
+ // 初始化侧边栏项目
+ SidebarItemsControl.ItemsSource = SidebarItems;
+ SidebarItems.Add(new SidebarItem() {
+ Type = SidebarItemType.Item,
+ Title = "启动时行为",
+ Name = "StartupItem",
+ IconSource = FindResource("StartupIcon") as DrawingImage,
+ Selected = false,
+ });
+ SidebarItems.Add(new SidebarItem() {
+ Type = SidebarItemType.Item,
+ Title = "画板和墨迹",
+ Name = "CanvasAndInkItem",
+ IconSource = FindResource("CanvasAndInkIcon") as DrawingImage,
+ Selected = false,
+ });
+ SidebarItems.Add(new SidebarItem() {
+ Type = SidebarItemType.Item,
+ Title = "手势操作",
+ Name = "GesturesItem",
+ IconSource = FindResource("GesturesIcon") as DrawingImage,
+ Selected = false,
+ });
+ SidebarItems.Add(new SidebarItem() {
+ Type = SidebarItemType.Separator
+ });
+ SidebarItems.Add(new SidebarItem() {
+ Type = SidebarItemType.Item,
+ Title = "个性化和外观",
+ Name = "AppearanceItem",
+ IconSource = FindResource("AppearanceIcon") as DrawingImage,
+ Selected = false,
+ });
+ SidebarItems.Add(new SidebarItem() {
+ Type = SidebarItemType.Item,
+ Title = "墨迹转形状",
+ Name = "InkRecognitionItem",
+ IconSource = FindResource("InkRecognitionIcon") as DrawingImage,
+ Selected = false,
+ });
+ SidebarItems.Add(new SidebarItem() {
+ Type = SidebarItemType.Item,
+ Title = "几何与形状绘制",
+ Name = "ShapeDrawingItem",
+ IconSource = FindResource("ShapeDrawingIcon") as DrawingImage,
+ Selected = false,
+ });
+ SidebarItems.Add(new SidebarItem() {
+ Type = SidebarItemType.Item,
+ Title = "自动化行为",
+ Name = "AutomationItem",
+ IconSource = FindResource("AutomationIcon") as DrawingImage,
+ Selected = false,
+ });
+ SidebarItems.Add(new SidebarItem() {
+ Type = SidebarItemType.Separator
+ });
+ SidebarItems.Add(new SidebarItem() {
+ Type = SidebarItemType.Item,
+ Title = "PowerPoint 支持",
+ Name = "PowerPointItem",
+ IconSource = FindResource("PowerPointIcon") as DrawingImage,
+ Selected = false,
+ });
+ SidebarItems.Add(new SidebarItem() {
+ Type = SidebarItemType.Item,
+ Title = "插件和脚本",
+ Name = "ExtensionsItem",
+ IconSource = FindResource("ExtensionsIcon") as DrawingImage,
+ Selected = false,
+ });
+ SidebarItems.Add(new SidebarItem() {
+ Type = SidebarItemType.Separator
+ });
+ SidebarItems.Add(new SidebarItem() {
+ Type = SidebarItemType.Item,
+ Title = "存储空间",
+ Name = "StorageItem",
+ IconSource = FindResource("StorageIcon") as DrawingImage,
+ Selected = false,
+ });
+ SidebarItems.Add(new SidebarItem() {
+ Type = SidebarItemType.Item,
+ Title = "截图和屏幕捕捉",
+ Name = "SnapshotItem",
+ IconSource = FindResource("SnapshotIcon") as DrawingImage,
+ Selected = false,
+ });
+ SidebarItems.Add(new SidebarItem() {
+ Type = SidebarItemType.Item,
+ Title = "点名器设置",
+ Name = "LuckyRandomItem",
+ IconSource = FindResource("LuckyRandomIcon") as DrawingImage,
+ Selected = false,
+ });
+ SidebarItems.Add(new SidebarItem() {
+ Type = SidebarItemType.Item,
+ Title = "高级选项",
+ Name = "AdvancedItem",
+ IconSource = FindResource("AdvancedIcon") as DrawingImage,
+ Selected = false,
+ });
+ SidebarItems.Add(new SidebarItem() {
+ Type = SidebarItemType.Item,
+ Title = "关于 InkCanvasForClass",
+ Name = "AboutItem",
+ IconSource = FindResource("AboutIcon") as DrawingImage,
+ Selected = false,
+ });
+ _selectedSidebarItemName = "AboutItem";
+ UpdateSidebarItemsSelection();
+
+ // 关于页面图片横幅
+ if (File.Exists(App.RootPath + "icc-about-illustrations.png")) {
+ try {
+ CopyrightBannerImage.Visibility = Visibility.Visible;
+ CopyrightBannerImage.Source =
+ new BitmapImage(new Uri($"file://{App.RootPath + "icc-about-illustrations.png"}"));
+ }
+ catch { }
+ } else {
+ CopyrightBannerImage.Visibility = Visibility.Collapsed;
+ }
+
+ // 关于页面构建时间
+ var buildTime = FileBuildTimeHelper.GetBuildDateTime(System.Reflection.Assembly.GetExecutingAssembly());
+ if (buildTime != null) {
+ var bt = ((DateTimeOffset)buildTime).LocalDateTime;
+ var m = bt.Month.ToString().PadLeft(2, '0');
+ var d = bt.Day.ToString().PadLeft(2, '0');
+ var h = bt.Hour.ToString().PadLeft(2, '0');
+ var min = bt.Minute.ToString().PadLeft(2, '0');
+ var s = bt.Second.ToString().PadLeft(2, '0');
+ AboutBuildTime.Text =
+ $"build-{bt.Year}-{m}-{d}-{h}:{min}:{s}";
+ }
+
+ // 关于页面系统版本
+ AboutSystemVersion.Text = $"{OSVersion.GetOperatingSystem()} {OSVersion.GetOSVersion().Version}";
+
+ // 关于页面触摸设备
+ var _t_touch = new Thread(() => {
+ var touchcount = TouchTabletDetectHelper.GetTouchTabletDevices().Count;
+ var support = TouchTabletDetectHelper.IsTouchEnabled();
+ Dispatcher.BeginInvoke(() =>
+ AboutTouchTabletText.Text = $"{touchcount}个设备,{(support ? "支持触摸设备" : "无触摸支持")}");
+ });
+ _t_touch.Start();
+ }
+
+ public enum SidebarItemType {
+ Item,
+ Separator
+ }
+
+ public class SidebarItem {
+ public SidebarItemType Type { get; set; }
+ public string Title { get; set; }
+ public string Name { get; set; }
+ public ImageSource IconSource { get; set; }
+ public bool Selected { get; set; }
+ public Visibility _spVisibility {
+ get => this.Type == SidebarItemType.Separator ? Visibility.Visible : Visibility.Collapsed;
+ }
+ public Visibility _siVisibility {
+ get => this.Type == SidebarItemType.Item ? Visibility.Visible : Visibility.Collapsed;
+ }
+
+ public SolidColorBrush _siBackground {
+ get => this.Selected
+ ? new SolidColorBrush(Color.FromRgb(217, 217, 217))
+ : new SolidColorBrush(Colors.Transparent);
+ }
+ }
+
+ public string _selectedSidebarItemName = "";
+ public ObservableCollection SidebarItems = new ObservableCollection();
+
+ public void UpdateSidebarItemsSelection() {
+ foreach (var si in SidebarItems) {
+ si.Selected = si.Name == _selectedSidebarItemName;
+ if (si.Selected) SettingsWindowTitle.Text = si.Title;
+ }
+ CollectionViewSource.GetDefaultView(SidebarItems).Refresh();
+ }
+
+ public static class TouchTabletDetectHelper {
+ [System.Runtime.InteropServices.DllImport("user32.dll")]
+ public static extern int GetSystemMetrics(int nIndex);
+
+ public static bool IsTouchEnabled()
+ {
+ const int MAXTOUCHES_INDEX = 95;
+ int maxTouches = GetSystemMetrics(MAXTOUCHES_INDEX);
+
+ return maxTouches > 0;
+ }
+
+ public class USBDeviceInfo
+ {
+ public USBDeviceInfo(string deviceID, string pnpDeviceID, string description)
+ {
+ this.DeviceID = deviceID;
+ this.PnpDeviceID = pnpDeviceID;
+ this.Description = description;
+ }
+ public string DeviceID { get; private set; }
+ public string PnpDeviceID { get; private set; }
+ public string Description { get; private set; }
+ }
+
+ public static List GetTouchTabletDevices()
+ {
+ List devices = new List();
+
+ ManagementObjectCollection collection;
+ using (var searcher = new ManagementObjectSearcher(@"Select * From Win32_PnPEntity"))
+ collection = searcher.Get();
+
+ foreach (var device in collection) {
+ var name = new StringBuilder((string)device.GetPropertyValue("Name")).ToString();
+ if (!name.Contains("Pentablet")) continue;
+ devices.Add(new USBDeviceInfo(
+ (string)device.GetPropertyValue("DeviceID"),
+ (string)device.GetPropertyValue("PNPDeviceID"),
+ (string)device.GetPropertyValue("Description")
+ ));
+ }
+
+ collection.Dispose();
+ return devices;
+ }
+ }
+
+ public static class FileBuildTimeHelper {
+ public struct _IMAGE_FILE_HEADER
+ {
+ public ushort Machine;
+ public ushort NumberOfSections;
+ public uint TimeDateStamp;
+ public uint PointerToSymbolTable;
+ public uint NumberOfSymbols;
+ public ushort SizeOfOptionalHeader;
+ public ushort Characteristics;
+ };
+
+ public static DateTimeOffset? GetBuildDateTime(Assembly assembly)
+ {
+ var path = assembly.Location;
+ if (File.Exists(path))
+ {
+ var buffer = new byte[Math.Max(Marshal.SizeOf(typeof(_IMAGE_FILE_HEADER)), 4)];
+ using (var fileStream = new FileStream(path, FileMode.Open, FileAccess.Read))
+ {
+ fileStream.Position = 0x3C;
+ fileStream.Read(buffer, 0, 4);
+ fileStream.Position = BitConverter.ToUInt32(buffer, 0); // COFF header offset
+ fileStream.Read(buffer, 0, 4); // "PE\0\0"
+ fileStream.Read(buffer, 0, buffer.Length);
+ }
+ var pinnedBuffer = GCHandle.Alloc(buffer, GCHandleType.Pinned);
+ try
+ {
+ var coffHeader = (_IMAGE_FILE_HEADER)Marshal.PtrToStructure(pinnedBuffer.AddrOfPinnedObject(), typeof(_IMAGE_FILE_HEADER));
+ return DateTimeOffset.FromUnixTimeSeconds(coffHeader.TimeDateStamp);
+ }
+ finally
+ {
+ pinnedBuffer.Free();
+ }
+ }
+ else
+ {
+ return null;
+ }
+ }
+ }
+
+ private Border _sidebarItemMouseDownBorder = null;
+
+ private void SidebarItem_MouseDown(object sender, MouseButtonEventArgs e) {
+ if (_sidebarItemMouseDownBorder != null || _sidebarItemMouseDownBorder == sender) return;
+ _sidebarItemMouseDownBorder = (Border)sender;
+ var bd = sender as Border;
+ if (bd.FindDescendantByName("MouseFeedbackBorder") is Border feedbackBd) feedbackBd.Opacity = 0.12;
+ }
+
+ private void SidebarItem_MouseUp(object sender, MouseButtonEventArgs e) {
+ if (_sidebarItemMouseDownBorder == null || _sidebarItemMouseDownBorder != sender) return;
+ if (_sidebarItemMouseDownBorder.Tag is SidebarItem data) _selectedSidebarItemName = data.Name;
+ SidebarItem_MouseLeave(sender, null);
+ UpdateSidebarItemsSelection();
+ }
+
+ private void SidebarItem_MouseLeave(object sender, MouseEventArgs e) {
+ if (_sidebarItemMouseDownBorder == null || _sidebarItemMouseDownBorder != sender) return;
+ if (_sidebarItemMouseDownBorder.FindDescendantByName("MouseFeedbackBorder") is Border feedbackBd) feedbackBd.Opacity = 0;
+ _sidebarItemMouseDownBorder = null;
+ }
+ }
+}
diff --git a/InkCanvasForClass/icc-about-illustrations.png b/InkCanvasForClass/icc-about-illustrations.png
new file mode 100644
index 0000000..43151b0
Binary files /dev/null and b/InkCanvasForClass/icc-about-illustrations.png differ