|
|
// Preview.cpp : implementation file
//
#include "stdafx.h"
#include "MSQSCAN.h"
#include "Preview.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__; #endif
/////////////////////////////////////////////////////////////////////////////
// CPreview
CPreview::CPreview() { m_hBitmap = NULL; }
CPreview::~CPreview() { }
void CPreview::GetSelectionRect(RECT *pRect) { CopyRect(pRect,&m_RectTracker.m_rect); }
void CPreview::SetSelectionRect(RECT *pRect) { CopyRect(&m_RectTracker.m_rect,pRect); InvalidateSelectionRect(); }
void CPreview::SetPreviewRect(CRect Rect) { m_PreviewRect.left = 0; m_PreviewRect.top = 0; m_PreviewRect.right = Rect.Width(); m_PreviewRect.bottom = Rect.Height(); //
// set selection rect styles
//
m_RectTracker.m_rect.left = PREVIEW_SELECT_OFFSET; m_RectTracker.m_rect.top = PREVIEW_SELECT_OFFSET; m_RectTracker.m_rect.right = Rect.Width()-PREVIEW_SELECT_OFFSET; m_RectTracker.m_rect.bottom = Rect.Height()-PREVIEW_SELECT_OFFSET; m_RectTracker.m_nStyle = CRectTracker::resizeInside|CRectTracker::dottedLine; m_RectTracker.SetClippingWindow(m_RectTracker.m_rect); }
BEGIN_MESSAGE_MAP(CPreview, CWnd) //{{AFX_MSG_MAP(CPreview)
ON_WM_LBUTTONDOWN() ON_WM_SETCURSOR() ON_WM_PAINT() //}}AFX_MSG_MAP
END_MESSAGE_MAP()
/////////////////////////////////////////////////////////////////////////////
// CPreview message handlers
void CPreview::OnLButtonDown(UINT nFlags, CPoint point) { m_RectTracker.Track(this,point,FALSE,this); InvalidateSelectionRect(); CWnd::OnLButtonDown(nFlags, point); }
BOOL CPreview::OnSetCursor(CWnd* pWnd, UINT nHitTest, UINT message) { if(m_RectTracker.SetCursor(pWnd,nHitTest)) return TRUE; return CWnd::OnSetCursor(pWnd, nHitTest, message); }
void CPreview::OnPaint() { CPaintDC dc(this); // device context for painting
if(m_hBitmap == NULL) { CRect TrueRect; GetWindowRect(TrueRect); //
// convert to client coords
//
CWnd* pParent = GetParent(); if(pParent) { ScreenToClient(TrueRect); //
// create a white brush
//
CBrush WhiteBrush; WhiteBrush.CreateSolidBrush(RGB(255,255,255)); //
// select white brush, while saving previously selected brush
//
CBrush* pOldBrush = dc.SelectObject(&WhiteBrush); //
// fill the preview window with white
//
dc.FillRect(TrueRect,&WhiteBrush); //
// put back the previously selected brush
//
dc.SelectObject(pOldBrush); //
// destroy the white brush
//
WhiteBrush.DeleteObject(); } } else {
//
// paint preview bitmap
//
PaintHBITMAPToDC(); }
//
// draw the selection rect, over the image
//
m_RectTracker.Draw(&dc); }
void CPreview::InvalidateSelectionRect() { //
// get parent window
//
CWnd* pParent = GetParent(); if(pParent) { //
// get your window rect
//
CRect TrueRect; GetWindowRect(TrueRect); //
// convert to client coords
//
pParent->ScreenToClient(TrueRect); //
// invalidate through parent, because we are using the parent's DC to
// draw images.
//
pParent->InvalidateRect(TrueRect); } }
void CPreview::SetHBITMAP(HBITMAP hBitmap) { m_hBitmap = hBitmap; PaintHBITMAPToDC(); }
void CPreview::PaintHBITMAPToDC() { //
// get hdc
//
HDC hMemorydc = NULL; HDC hdc = ::GetWindowDC(m_hWnd); BITMAP bitmap;
if(hdc != NULL){ //
// create a memory dc
//
hMemorydc = ::CreateCompatibleDC(hdc); if(hMemorydc != NULL){ //
// select HBITMAP into your hMemorydc
//
if(::GetObject(m_hBitmap,sizeof(BITMAP),(LPSTR)&bitmap) != 0) { HGDIOBJ hGDIObj = ::SelectObject(hMemorydc,m_hBitmap); RECT ImageRect; ImageRect.top = 0; ImageRect.left = 0; ImageRect.right = bitmap.bmWidth; ImageRect.bottom = bitmap.bmHeight; ScaleBitmapToDC(hdc,hMemorydc,&m_PreviewRect,&ImageRect); } else { OutputDebugString(TEXT("Failed GetObject\n")); } } //
// delete hMemorydc
//
::DeleteDC(hMemorydc); } //
// delete hdc
//
::ReleaseDC(m_hWnd,hdc); }
void CPreview::ScreenRectToClientRect(HWND hWnd,LPRECT pRect) { POINT PtConvert;
PtConvert.x = pRect->left; PtConvert.y = pRect->top;
//
// convert upper left point
//
::ScreenToClient(hWnd,&PtConvert);
pRect->left = PtConvert.x; pRect->top = PtConvert.y;
PtConvert.x = pRect->right; PtConvert.y = pRect->bottom;
//
// convert lower right point
//
::ScreenToClient(hWnd,&PtConvert);
pRect->right = PtConvert.x; pRect->bottom = PtConvert.y;
pRect->bottom-=1; pRect->left+=1; pRect->right-=1; pRect->top+=1; }
void CPreview::ScaleBitmapToDC(HDC hDC, HDC hDCM, LPRECT lpDCRect, LPRECT lpDIBRect) { ::SetStretchBltMode(hDC, COLORONCOLOR);
if ((RECTWIDTH(lpDCRect) == RECTWIDTH(lpDIBRect)) && (RECTHEIGHT(lpDCRect) == RECTHEIGHT(lpDIBRect))) ::BitBlt (hDC, // hDC
lpDCRect->left, // DestX
lpDCRect->top, // DestY
RECTWIDTH(lpDCRect), // nDestWidth
RECTHEIGHT(lpDCRect), // nDestHeight
hDCM, 0, 0, SRCCOPY); else { StretchBlt(hDC, // hDC
lpDCRect->left, // DestX
lpDCRect->top, // DestY
lpDCRect->right,//ScaledWidth, // nDestWidth
lpDCRect->bottom,//ScaledHeight, // nDestHeight
hDCM, 0, // SrcX
0, // SrcY
RECTWIDTH(lpDIBRect), // wSrcWidth
RECTHEIGHT(lpDIBRect), // wSrcHeight
SRCCOPY); // dwROP
} } /////////////////////////////////////////////////////////////////////////////
// CRectTrackerEx overridden functions
void CRectTrackerEx::AdjustRect( int nHandle, LPRECT lpRect ) { //
// if clipping rect is empty, do nothing
//
if (!m_rectClippingWindow.IsRectEmpty()) { if (nHandle == hitMiddle) {
// user is dragging entire selection around...
// make sure selection rect does not get out of clipping
// rect
//
CRect rect = lpRect; if (rect.right > m_rectClippingWindow.right) rect.OffsetRect(m_rectClippingWindow.right - rect.right, 0); if (rect.left < m_rectClippingWindow.left) rect.OffsetRect(m_rectClippingWindow.left - rect.left, 0); if (rect.bottom > m_rectClippingWindow.bottom) rect.OffsetRect(0, m_rectClippingWindow.bottom - rect.bottom); if (rect.top < m_rectClippingWindow.top) rect.OffsetRect(0, m_rectClippingWindow.top - rect.top); *lpRect = rect; } else {
//
// user is resizing the selection rect
// make sure selection rect does not extend outside of clipping
// rect
//
int *px, *py;
//
// get X and Y selection axis
//
GetModifyPointers(nHandle, &px, &py, NULL, NULL);
if (px != NULL) *px = max(min(m_rectClippingWindow.right, *px), m_rectClippingWindow.left); if (py != NULL) *py = max(min(m_rectClippingWindow.bottom, *py), m_rectClippingWindow.top);
CRect rect = lpRect;
//
// check/adjust X axis
//
if (px != NULL && abs(rect.Width()) < m_sizeMin.cx) { if (*px == rect.left) rect.left = rect.right; else rect.right = rect.left; }
//
// check/adjust Y axis
//
if (py != NULL && abs(rect.Height()) < m_sizeMin.cy) { if (*py == rect.top) rect.top = rect.bottom; else rect.bottom = rect.top; }
//
// save the adjusted rectangle
//
*lpRect = rect; } } }
void CRectTrackerEx::SetClippingWindow(CRect Rect) { m_rectClippingWindow = Rect; }
|