Initial commit to new repository
This commit is contained in:
135
src/AxCopilot/Views/EyeDropperWindow.xaml.cs
Normal file
135
src/AxCopilot/Views/EyeDropperWindow.xaml.cs
Normal file
@@ -0,0 +1,135 @@
|
||||
using System.Drawing;
|
||||
using System.Drawing.Imaging;
|
||||
using System.IO;
|
||||
using System.Runtime.InteropServices;
|
||||
using System.Windows;
|
||||
using System.Windows.Controls;
|
||||
using System.Windows.Input;
|
||||
using System.Windows.Media;
|
||||
using System.Windows.Media.Imaging;
|
||||
|
||||
namespace AxCopilot.Views;
|
||||
|
||||
/// <summary>
|
||||
/// 전체 화면 스포이드 모드. 마우스를 따라다니는 돋보기와 HEX 코드를 표시하고,
|
||||
/// 클릭 시 해당 픽셀 색상을 캡처하여 ColorPickResultWindow를 표시합니다.
|
||||
/// </summary>
|
||||
public partial class EyeDropperWindow : Window
|
||||
{
|
||||
[DllImport("user32.dll")]
|
||||
private static extern bool GetCursorPos(out POINT lpPoint);
|
||||
|
||||
[DllImport("gdi32.dll")]
|
||||
private static extern uint GetPixel(IntPtr hdc, int x, int y);
|
||||
|
||||
[DllImport("user32.dll")]
|
||||
private static extern IntPtr GetDC(IntPtr hWnd);
|
||||
|
||||
[DllImport("user32.dll")]
|
||||
private static extern int ReleaseDC(IntPtr hWnd, IntPtr hDC);
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
private struct POINT { public int X, Y; }
|
||||
|
||||
/// <summary>클릭으로 선택된 색상. null이면 취소.</summary>
|
||||
public System.Drawing.Color? PickedColor { get; private set; }
|
||||
public double PickX { get; private set; }
|
||||
public double PickY { get; private set; }
|
||||
|
||||
private readonly System.Drawing.Rectangle _screenBounds;
|
||||
|
||||
public EyeDropperWindow()
|
||||
{
|
||||
InitializeComponent();
|
||||
|
||||
// 전체 모니터 영역
|
||||
_screenBounds = GetAllScreenBounds();
|
||||
Left = _screenBounds.X;
|
||||
Top = _screenBounds.Y;
|
||||
Width = _screenBounds.Width;
|
||||
Height = _screenBounds.Height;
|
||||
|
||||
Loaded += (_, _) =>
|
||||
{
|
||||
Magnifier.Visibility = Visibility.Visible;
|
||||
HexLabel.Visibility = Visibility.Visible;
|
||||
};
|
||||
}
|
||||
|
||||
private void Window_MouseMove(object sender, MouseEventArgs e)
|
||||
{
|
||||
var pos = e.GetPosition(RootCanvas);
|
||||
var color = GetScreenPixelColor();
|
||||
|
||||
// 돋보기 위치 (커서 오른쪽 위)
|
||||
Canvas.SetLeft(Magnifier, pos.X + 16);
|
||||
Canvas.SetTop(Magnifier, pos.Y - 100);
|
||||
|
||||
// HEX 레이블 위치
|
||||
Canvas.SetLeft(HexLabel, pos.X + 16);
|
||||
Canvas.SetTop(HexLabel, pos.Y - 10);
|
||||
|
||||
// 돋보기 색상 미리보기
|
||||
var wpfColor = System.Windows.Media.Color.FromRgb(color.R, color.G, color.B);
|
||||
MagPreview.Fill = new SolidColorBrush(wpfColor);
|
||||
HexLabelText.Text = $"#{color.R:X2}{color.G:X2}{color.B:X2}";
|
||||
}
|
||||
|
||||
private void Window_MouseDown(object sender, MouseButtonEventArgs e)
|
||||
{
|
||||
if (e.ChangedButton == MouseButton.Left)
|
||||
{
|
||||
PickedColor = GetScreenPixelColor();
|
||||
GetCursorPos(out var pt);
|
||||
PickX = pt.X;
|
||||
PickY = pt.Y;
|
||||
Close();
|
||||
}
|
||||
else if (e.ChangedButton == MouseButton.Right)
|
||||
{
|
||||
PickedColor = null;
|
||||
Close();
|
||||
}
|
||||
}
|
||||
|
||||
private void Window_KeyDown(object sender, KeyEventArgs e)
|
||||
{
|
||||
if (e.Key == Key.Escape)
|
||||
{
|
||||
PickedColor = null;
|
||||
Close();
|
||||
}
|
||||
}
|
||||
|
||||
private static System.Drawing.Color GetScreenPixelColor()
|
||||
{
|
||||
GetCursorPos(out var pt);
|
||||
var hdc = GetDC(IntPtr.Zero);
|
||||
try
|
||||
{
|
||||
uint pixel = GetPixel(hdc, pt.X, pt.Y);
|
||||
int r = (int)(pixel & 0xFF);
|
||||
int g = (int)((pixel >> 8) & 0xFF);
|
||||
int b = (int)((pixel >> 16) & 0xFF);
|
||||
return System.Drawing.Color.FromArgb(r, g, b);
|
||||
}
|
||||
finally
|
||||
{
|
||||
ReleaseDC(IntPtr.Zero, hdc);
|
||||
}
|
||||
}
|
||||
|
||||
private static System.Drawing.Rectangle GetAllScreenBounds()
|
||||
{
|
||||
int left = 0, top = 0, right = 0, bottom = 0;
|
||||
foreach (var screen in System.Windows.Forms.Screen.AllScreens)
|
||||
{
|
||||
var b = screen.Bounds;
|
||||
left = Math.Min(left, b.Left);
|
||||
top = Math.Min(top, b.Top);
|
||||
right = Math.Max(right, b.Right);
|
||||
bottom = Math.Max(bottom, b.Bottom);
|
||||
}
|
||||
return new System.Drawing.Rectangle(left, top, right - left, bottom - top);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user