📄 colorpickerdlg.cpp
字号:
// ColorPickerDlg.cpp : implementation file
//
#include "stdafx.h"
#include "ColorSpace.h"
#include "ColorPickerDlg.h"
#include "Common.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
#define RADUIS 100
#define IN_CIRCLE 1
#define IN_BRIGHT 2
#define IN_NOTHING 0
/////////////////////////////////////////////////////////////////////////////
// CColorPickerDlg dialog
CColorPickerDlg::CColorPickerDlg(COLORREF c,CWnd* pParent /*=NULL*/)
: CDialog(CColorPickerDlg::IDD, pParent)
{
//{{AFX_DATA_INIT(CColorPickerDlg)
// NOTE: the ClassWizard will add member initialization here
//}}AFX_DATA_INIT
Vertex = CPoint(102,108);
Top = CPoint(102,9);
Left = CPoint(23,147);
Right = CPoint(181,147);
color.r = GetRValue(c);
color.g = GetGValue(c);
color.b = GetBValue(c);
m_OldColor = color;
hsvColor = color.toHSV();
m_bInMouse = FALSE;
m_bInitOver = FALSE;
m_bInDrawAll = FALSE;
}
CColorPickerDlg::~CColorPickerDlg()
{
if(m_RgbBitmap.GetSafeHandle())
{
m_RgbBitmap.DeleteObject();
}
if(m_HsbBitmap.GetSafeHandle())
{
m_HsbBitmap.DeleteObject();
}
}
void CColorPickerDlg::DoDataExchange(CDataExchange* pDX)
{
CDialog::DoDataExchange(pDX);
//{{AFX_DATA_MAP(CColorPickerDlg)
// NOTE: the ClassWizard will add DDX and DDV calls here
//}}AFX_DATA_MAP
}
BEGIN_MESSAGE_MAP(CColorPickerDlg, CDialog)
//{{AFX_MSG_MAP(CColorPickerDlg)
ON_WM_LBUTTONDOWN()
ON_WM_LBUTTONUP()
ON_WM_MOUSEMOVE()
ON_WM_SYSCOLORCHANGE()
ON_WM_PAINT()
ON_EN_CHANGE(IDC_EDIT_BLUE, OnChangeEditBlue)
ON_EN_CHANGE(IDC_EDIT_GREEN, OnChangeEditGreen)
ON_EN_CHANGE(IDC_EDIT_HUE, OnChangeEditHue)
ON_EN_CHANGE(IDC_EDIT_RED, OnChangeEditRed)
ON_EN_CHANGE(IDC_EDIT_SAT, OnChangeEditSat)
ON_EN_CHANGE(IDC_EDIT_VAL, OnChangeEditVal)
//}}AFX_MSG_MAP
END_MESSAGE_MAP()
/////////////////////////////////////////////////////////////////////////////
// CColorPickerDlg message handlers
void CColorPickerDlg::OnLButtonDown(UINT nFlags, CPoint point)
{
if(hsbRect.PtInRect(point))
{
m_bInMouse = FALSE;
if(InCircle(point))
{
m_nMouseIn = IN_CIRCLE;
}
else
if(InBright(point))
{
m_nMouseIn = IN_BRIGHT;
}
else
{
m_nMouseIn = IN_NOTHING;
}
if(m_nMouseIn)
{
SetCapture();
TrackPoint(point);
}
}
else
if(rgbRect.PtInRect(point))
{
m_nMouseIn = IN_NOTHING;
if(rects[RED].PtInRect(point))
{
SetCapture();
m_bInMouse = TRUE;
nIndex = RED;
}
else
if(rects[GREEN].PtInRect(point))
{
SetCapture();
m_bInMouse = TRUE;
nIndex = GREEN;
}
else
if(rects[BLUE].PtInRect(point))
{
SetCapture();
m_bInMouse = TRUE;
nIndex = BLUE;
}
}
CDialog::OnLButtonDown(nFlags, point);
}
void CColorPickerDlg::OnLButtonUp(UINT nFlags, CPoint point)
{
if(GetCapture() == this)
{
ReleaseCapture();
m_bInMouse = FALSE;
}
CDialog::OnLButtonUp(nFlags, point);
}
void CColorPickerDlg::OnMouseMove(UINT nFlags, CPoint point)
{
if(GetCapture() == this && m_nMouseIn)
{
TrackPoint(point);
}
else
if(GetCapture() == this && m_bInMouse)
{
double val;
BOOL bChange = FALSE;
if(nIndex == RED)
{
if(point.y > Vertex.y)
{
point.y = Vertex.y;
}
point.x = Vertex.x;
val = Distance(point,Vertex);
if(val > RedLen)
{
val = RedLen;
}
CClientDC dc(this);
DrawLines(&dc);
val = (val/RedLen)*255;
color.r = (int)val;
CPoint pt;
pt = PointOnLine(Vertex,Top,(color.r*RedLen)/255,RedLen);
rects[RED] = CRect(pt.x - RECT_WIDTH ,pt.y-RECT_WIDTH ,pt.x+RECT_WIDTH ,pt.y+RECT_WIDTH );
CalcCuboid();
DrawLines(&dc);
bChange = TRUE;
}
else
if(nIndex == GREEN)
{
if(point.x > Vertex.x)
{
point.x = Vertex.x;
}
point.y = rects[GREEN].top + RECT_WIDTH;
val = Distance(point,Vertex);
if(val > GreenLen)
{
val = GreenLen;
}
CClientDC dc(this);
DrawLines(&dc);
val = (val/GreenLen)*255;
color.g = (int)val;
CPoint pt;
pt = PointOnLine(Vertex,Left,(color.g*GreenLen)/255,GreenLen);
rects[GREEN] = CRect(pt.x - RECT_WIDTH ,pt.y-RECT_WIDTH ,pt.x+RECT_WIDTH ,pt.y+RECT_WIDTH );
CalcCuboid();
DrawLines(&dc);
bChange = TRUE;
}
else
if(nIndex == BLUE)
{
if(point.x < Vertex.x)
{
point.x = Vertex.x;
}
point.y = rects[BLUE].top + RECT_WIDTH;
val = Distance(point,Vertex);
if(val > BlueLen)
{
val = BlueLen;
}
CClientDC dc(this);
DrawLines(&dc);
val = (val/BlueLen)*255;
color.b = (int)val;
CPoint pt;
pt = PointOnLine(Vertex,Right,(color.b*GreenLen)/255,BlueLen);
rects[BLUE] = CRect(pt.x - RECT_WIDTH ,pt.y-RECT_WIDTH ,pt.x+RECT_WIDTH ,pt.y+RECT_WIDTH );
CalcCuboid();
DrawLines(&dc);
bChange = TRUE;
}
if(bChange)
{
hsvColor = color.toHSV();
SetEditVals();
CClientDC dc(this);
DrawMarkers(&dc);
CalcRects();
SetDIBPalette();
InvalidateRect(&brightRect,FALSE);
DrawHSB(&dc);
}
}
CDialog::OnMouseMove(nFlags, point);
}
void CColorPickerDlg::OnPaint()
{
CPaintDC dc(this); // device context for painting
DrawFilledColor(&dc,OldColorRect,m_OldColor.color());
DrawHSB(&dc);
DrawRGB(&dc);
}
BOOL CColorPickerDlg::OnInitDialog()
{
CDialog::OnInitDialog();
GetDlgItem(IDC_STATIC_RGB_RECT)->GetWindowRect(&rgbRect);
GetDlgItem(IDC_STATIC_HSB_RECT)->GetWindowRect(&hsbRect);
ScreenToClient(&rgbRect);
ScreenToClient(&hsbRect);
GetDlgItem(IDC_STATIC_OLD)->GetWindowRect(&OldColorRect);
GetDlgItem(IDC_STATIC_NEW)->GetWindowRect(&NewColorRect);
ScreenToClient(&OldColorRect);
ScreenToClient(&NewColorRect);
CWindowDC dc(NULL);
CSize bmSize;
// Set Up HSB
memDC.CreateCompatibleDC(&dc);
LoadMappedBitmap(m_HsbBitmap,IDB_BITMAP_HSB,bmSize);
hsbWidth = bmSize.cx;
hsbHeight = bmSize.cy;
hsbRect.InflateRect(-5,-5);
hsbRect.top += 20;
hsbRect.left += 10;
m_Centre = CPoint(RADIUS,RADIUS);
m_Centre += CPoint(hsbRect.left,hsbRect.top);
brightRect = CRect(hsbRect.left+hsbWidth+20,hsbRect.top,hsbRect.left+hsbWidth+20+20,hsbRect.top + hsbHeight);
CreateBrightDIB();
CalcRects();
SetDIBPalette();
// Set Up RGB
LoadMappedBitmap(m_RgbBitmap,IDB_BITMAP_RGB,bmSize);
rgbWidth = bmSize.cx;
rgbHeight = bmSize.cy;
rgbRect.InflateRect(-5,-5);
rgbRect.top+=10;
rgbRect.left-=3;
CPoint pt = CPoint(rgbRect.left,rgbRect.top);
Top += pt;
Left += pt;
Right += pt;
Vertex += pt;
// TODO: Add your specialized code here and/or call the base class
RedLen = Distance(Vertex,Top);
GreenLen = Distance(Vertex,Left);
BlueLen = Distance(Vertex,Right);
CalcSlopes();
CalcCuboid();
SetSpinVals();
SetEditVals();
m_bInitOver = TRUE;
return TRUE; // return TRUE unless you set the focus to a control
// EXCEPTION: OCX Property Pages should return FALSE
}
void CColorPickerDlg::DrawMarkers(CDC *pDC)
{
if(m_CurrentRect.Width())
{
CPen *oldPen;
CBrush *oldBrush;
int oldMode;
CRect cr = m_CurrentRect;
oldPen = (CPen *)pDC->SelectStockObject(WHITE_PEN);
oldBrush = (CBrush *)pDC->SelectStockObject(NULL_BRUSH);
oldMode = pDC->SetROP2(R2_XORPEN);
pDC->Rectangle(&cr);
CPen pen;
pen.CreatePen(PS_SOLID,2,RGB(255,255,255));
pDC->SelectObject(&pen);
pDC->Rectangle(&brightMark);
pDC->SelectObject(oldPen);
pDC->SelectObject(oldBrush);
pDC->SetROP2(oldMode);
pen.DeleteObject();
}
}
BOOL CColorPickerDlg::InCircle(CPoint pt)
{
return Distance(pt,m_Centre) <= RADIUS;
}
BOOL CColorPickerDlg::InBright(CPoint pt)
{
return brightRect.PtInRect(pt);
}
void CColorPickerDlg::TrackPoint(CPoint pt)
{
if(m_nMouseIn == IN_CIRCLE)
{
CClientDC dc(this);
DrawMarkers(&dc);
hsvColor.h = (int)RAD2DEG(AngleFromPoint(pt,m_Centre));
if(hsvColor.h < 0)
{
hsvColor.h += 360;
}
hsvColor.s = (int)SCALETOMAX(Distance(pt,m_Centre));
if(hsvColor.s > 255) hsvColor.s = 255;
SetDIBPalette();
CalcRects();
InvalidateRect(&brightRect,FALSE);
DrawMarkers(&dc);
color = hsvColor.toRGB();
SetEditVals();
DrawLines(&dc);
CalcCuboid();
DrawRGB(&dc);
}
else
if(m_nMouseIn == IN_BRIGHT)
{
double d;
d = brightRect.bottom - pt.y;
d *= 255;
d /= brightRect.Height();
if(d < 0 ) d = 0;
if(d > 255) d = 255;
CClientDC dc(this);
DrawMarkers(&dc);
hsvColor.v = (int)d;
CalcRects();
DrawMarkers(&dc);
color = hsvColor.toRGB();
SetEditVals();
DrawLines(&dc);
CalcCuboid();
DrawRGB(&dc);
}
}
void CColorPickerDlg::CreateBrightDIB()
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -