Pixel Color UnderMouse
This is a feature that I wanted for a tool I’m doing. I have a color selection control that can select the color of the pixel under the mouse position from the entire application window. I searched the web for a solution and I found a cool implementation from theWPFblog, as Lee Brimelow explains:
“I tried many different ways of doing this but the cleanest was to use the CroppedBitmap class. As you can see in the code below, I first pull out a 1×1 pixel cropped bitmap from the color picker image that is directly below the mouse. Then it’s just a matter of copying the 1 pixel into a byte array and reading the RGB values. There are 4 bytes in every pixel which corresponds to the RGB colors and 1 byte for alpha. To change the color of the rectangle I simply create a new SolidColorBrush from the RGB values. I can think of many great uses for this! Click on the image at the left to check out the app. The C# source code is listed below so you can check out exactly how I implemented it.“
The code can be found here.
Another Alternative
Lee’s solution is not good enough for me because I need a color from a pixel found in the entire client area of my application, and Lee’s solution forces me to have a BitmapSource to take the pixel from it.
I found a cleanest way to do that, maybe not clean in “WPF” speaking but using only three simple Win32 functions:
private struct POINT{ public uint X; public uint Y;}[DllImport("gdi32")]private static extern int GetPixel(int hdc, int nXPos,int nYPos);[DllImport("user32")]private static extern int GetWindowDC(int hwnd);[DllImport("user32")]private static extern int GetCursorPos(out POINTAPI lpPoint);[DllImport("user32")]private static extern int ReleaseDC(int hWnd, int hDC);
And here is the GetPixelColor method implementation:
private static SolidColorBrush GetPixelColor(Point point){ int lDC = GetWindowDC( 0 ); int intColor = GetPixel( lDC, (int)point.X, (int)point.Y ); // // Release the DC after getting the Color. ReleaseDC( 0, lDC ); //byte a = (byte)( ( intColor >> 0x18 ) & 0xffL ); byte b = (byte)( ( intColor >> 0x10 ) & 0xffL ); byte g = (byte)( ( intColor >> 8 ) & 0xffL ); byte r = (byte)( intColor & 0xffL ); Color color = Color.FromRgb( r, g, b ); return new SolidColorBrush( color );}
With GetWindowDC( 0 ) I ask for the entire window DC, which then I use with GetPixelColor that retrieves the color value from position.
The System.Windows.Media.Color class in WPF doesn’t have a FromArgb method that accepts a integer value of the color as its counterpart from System.Drawing.Color, so I break apart the RGB components from integer value.
Using it:
protected override void OnMouseMove(MouseEventArgs e)
{
POINT point;
GetCursorPos( out point );
Point pos = new Point( point.X, point.Y );
this.StrokeBrush = GetPixelColor( pos );
}
This is an alternative solution, for getting the color under the mouse position even when you don’t have a BitmapSource to take it from or you are mixing WinForms or Win32 with WPF.
Have fun!
'Computer Science' 카테고리의 다른 글
flash plot (0) | 2009.04.21 |
---|---|
contextmenustrip 메뉴에 하위메뉴 동적으로 생성 (0) | 2009.04.15 |
[C#]마우스 좌표 얻기 (0) | 2009.04.08 |
EVC 4.0 프로그래밍의 준비 (0) | 2009.04.06 |
액션 스크립트 용어 및 정리 (0) | 2009.03.17 |