You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
kev/Drawer/Module/GeoSigmaDraw/ItemCopyAsImageEx.cpp

517 lines
14 KiB
C++

#include "stdafx.h"
#include "SigmaDoc.h"
#include "ItemCopyAsImageEx.h"
#include "ItemExportFile.H"
#include "MxnFormat\AxisLayout.h"
#include "gdiplus.h"
using namespace Gdiplus;
NItem::CItemCopyAsImageEx::CItemCopyAsImageEx(CSigmaDoc * ppDoc)
: CItemRectTracker(ppDoc)
, m_color(0)
, m_ShowProportion(false)
, m_ShowNetGrid(false)
{
this->SetType(ITEM_COPY_AS_IMAGE_EX);
m_coorRect.Empty();
m_Proportion.m_dScaleLength = 2000;
}
NItem::CItemCopyAsImageEx::~CItemCopyAsImageEx()
{
}
void NItem::CItemCopyAsImageEx::SetProportionVisible(bool visible) {
m_ShowProportion = visible;
}
void NItem::CItemCopyAsImageEx::SetNetGridVisible(bool visible) {
m_ShowNetGrid = visible;
}
void NItem::CItemCopyAsImageEx::SetNetGridParameter(RectangularCSGridData* pData)
{
// 网格颜色
m_color = RGB(pData->girdColorR, pData->girdColorG, pData->girdColorB);
// 网格步长
m_Net.m_step.SetSize(pData->stepX, pData->stepY);
m_Net.ScaleProperty(1000, 1000);
m_Net.SetProjection(&(GetDoc()->GetDraw()->m_ExchangeXYZ));
// 基数
m_Net.m_ptBase.x0 = pData->baseX;
m_Net.m_ptBase.y0 = pData->baseY;
// 系数
m_Net.m_szCoefficient.cx = pData->coefficientX;
m_Net.m_szCoefficient.cy = pData->coefficientY;
// 文字尺寸
m_Net.m_szText.cy = pData->textHeight;
m_Net.m_szText.cx = pData->textHeight*0.4;
// 文字刻度方式
switch (pData->textScale)
{
case 0: m_Net.SetTextMode(CNet::textGeography); break;//地理
case 1: m_Net.SetTextMode(CNet::textMath); break;//数学
case 2: m_Net.SetTextMode(CNet::textGeography1); break;//地理1
default:
case 3: m_Net.SetTextMode(CNet::textGeography2); break;//地理2(all)
}
// 坐标网显示方式
switch (pData->showMode)
{
default:
case 0: m_Net.SetDisplayMode(CNet::showLine); break;//显示曲线
case 1: m_Net.SetDisplayMode(CNet::showCrossPoint); break;//显示交点
case 2: m_Net.SetDisplayMode(CNet::showNull); break;//显示为空1
}
// 外边框
m_Net.EnableOutFrame(pData->isShowOutBorder ? true : false); // 是否显示
COLORREF colFrame = RGB(pData->borderColorR, pData->borderColorG, pData->borderColorB);
m_Net.SetFrameColor(colFrame); // 边框颜色
m_Net.GetOutFrame()->EnableBlackLine(pData->blackOutterBorder); // 显示黑边框
m_Net.GetOutFrame()->thickness = GetUnitMode().toRealUnit(pData->borderThickness); // 边框厚度
}
void NItem::CItemCopyAsImageEx::Clear() {
//m_range.SetRectEmpty();
m_coorRect.Empty();
}
int NItem::CItemCopyAsImageEx::SetRange(CRect rect)
{
//GetDoc()->SetCapturedScreenStatus(false);
if (rect.IsRectEmpty())
{
m_range.SetRectEmpty();
//m_pTracker->Reset();
return -1;
}
m_range = rect;
m_coorRect = GetDC()->GetReal(rect);
// 自动计算坐标网的尺寸
//(CRect8)m_Net = m_coorRect;
m_Net.left = m_coorRect.left;
m_Net.right = m_coorRect.right;
m_Net.top = m_coorRect.top;
m_Net.bottom = m_coorRect.bottom;
CAxisLayout al(m_coorRect.left, m_coorRect.right, 1);
TIntervalStep<double> sx = al.sd;
al.setDataRange(m_coorRect.bottom, m_coorRect.top, 1);
double step = min(sx.step, al.sd.step);
m_Net.m_step.SetSize(step, step);
m_Net.SetDisplayMode(CNet::showNull);
//自动根据单位设置文字大小
double scale = GetDoc()->GetCurrentUnitScale();
m_Net.ScaleProperty(scale, scale);
//m_pTracker->Create(m_pDoc, m_range);
//CopySelectedToClipboard();
//GetDoc()->SetCapturedScreenStatus(true);
return 1;
}
void NItem::CItemCopyAsImageEx::GetRange(CRect8* rec) {
rec->left = m_coorRect.left;
rec->right = m_coorRect.right;
rec->bottom = m_coorRect.bottom;
rec->top = m_coorRect.top;
}
void NItem::CItemCopyAsImageEx::Refresh(CDC* pDC) {
if (m_coorRect.IsEmpty())
return;
m_tracker.m_rect = GetDC()->GetScreen(m_coorRect);
CPoint2D ptCenter = m_coorRect.CenterPoint();
// 绘制坐标框
// 绘制比例尺
if (m_ShowProportion) {
CRect8 rct = m_Proportion.GetRect();
double dWidth = rct.Width();
double dHeight = rct.Height();
double dX = ptCenter.x0 - dWidth * 0.5;
double dY = m_coorRect.top + dHeight * 0.3;
m_Proportion.x0 = dX;
m_Proportion.y0 = dY;
CDC* pDCOld = GetDC()->GetDC();
GetDC()->Create(pDC);
GetDC()->Draw(m_Proportion, m_color);
GetDC()->Create(pDCOld);
}
if (m_ShowNetGrid)
{
// 自动计算坐标网的尺寸
(CRect8)m_Net = m_coorRect;
//if (!GetDoc()->GetDraw()->GetProjection().IsEmpty())
//{
// m_Net.SetProjection(&(GetDoc()->GetDraw()->m_ExchangeXYZ));
// //自动计算步长
// CRect8 rectBL = m_Net.GetRangeBL();
// double step = min(rectBL.Width() / 5, rectBL.Height() / 5);
// step *= 60; //转换为分单位
// step = AfxGetPublicFunction()->GetLBStep(step);
// m_Net.m_step.SetSize(step, step);
//}
////自动根据单位设置文字大小
//double scale = GetDoc()->GetCurrentUnitScale();
//m_Net.ScaleProperty(scale, scale);
CDC* pDCOld = GetDC()->GetDC();
GetDC()->Create(pDC);
GetDC()->Draw(m_Net, m_color, m_color);
GetDC()->Create(pDCOld);
}
}
void NItem::CItemCopyAsImageEx::GetTrueRect(CRect8* lpTrueRect)
{
*lpTrueRect = m_coorRect;
if (m_ShowNetGrid) {
m_Net.GetRange(*lpTrueRect);
lpTrueRect->right += 1;
}
if (m_ShowProportion) {
CRect8 rct;
rct = m_Proportion.GetRect();
lpTrueRect->top = rct.top;
}
}
void NItem::CItemCopyAsImageEx::DrawShadow(CDC *pDC, CRect &rectScreen, CRect rectCenter)
{
Gdiplus::SolidBrush brushTrans(Gdiplus::Color(228, 255, 255, 255));
Gdiplus::Graphics graphics(pDC->m_hDC);
graphics.FillRectangle(&brushTrans, 0, 0, rectScreen.right, rectCenter.top);
graphics.FillRectangle(&brushTrans, 0, rectCenter.top, rectCenter.left, rectCenter.bottom - rectCenter.top);
graphics.FillRectangle(&brushTrans, rectCenter.right, rectCenter.top
, rectScreen.right - rectCenter.right, rectCenter.bottom - rectCenter.top);
graphics.FillRectangle(&brushTrans, 0, rectCenter.bottom
, rectScreen.right, rectScreen.bottom - rectCenter.bottom);
}
void NItem::CItemCopyAsImageEx::DrawNetGrid(CDC* pDC)
{
// 自动计算坐标网的尺寸
m_Net.left = m_coorRect.left;
m_Net.right = m_coorRect.right;
m_Net.top = m_coorRect.top;
m_Net.bottom = m_coorRect.bottom;
CDC* pDCOld = GetDC()->GetDC();
GetDC()->Create(pDC);
GetDC()->Draw(m_Net, m_color, m_color);
GetDC()->Create(pDCOld);
}
void NItem::CItemCopyAsImageEx::DrawScaleBar(CDC* pDC)
{
if (m_Proportion.m_size.cx <= 0 || m_Proportion.m_size.cy <= 0)
{
double dx = m_Proportion.m_dScaleLength * m_Proportion.m_dCoefficient;
m_Proportion.m_size.cy = dx * 0.2;// 0.1
m_Proportion.m_size.cx = m_Proportion.m_size.cy * 0.4;
}
CPoint2D ptCenter = m_coorRect.CenterPoint();
CRect8 rct;
// m_Proportion.GetRange(rct);
rct = m_Proportion.GetRect();
double dWidth = rct.Width();
double dHeight = rct.Height();
double dX = ptCenter.x0 - dWidth * 0.5;
double dY = m_coorRect.top + dHeight * 0.3;
m_Proportion.x0 = dX;
m_Proportion.y0 = dY;
if (m_ShowNetGrid) {
CRect8 rectFrm;
m_Net.GetRange(rectFrm);
m_Proportion.y0 = rectFrm.top + dHeight * 0.2;
}
CDC* pDCOld = GetDC()->GetDC();
GetDC()->Create(pDC);
GetDC()->Draw(m_Proportion, m_Proportion.color);
GetDC()->Create(pDCOld);
}
void NItem::CItemCopyAsImageEx::OnDraw(CXyDC * pXyDC, CDC* pDC)
{
if (m_coorRect.IsEmpty())
return;
m_tracker.m_rect = GetDC()->GetScreen(m_coorRect);
CRect rectCenter = m_tracker.m_rect;
CRect rectScreen = GetDC()->GetViewRect();
DrawShadow(pDC, rectScreen, rectCenter);
// 绘制坐标框
if (m_ShowNetGrid)
{
DrawNetGrid(pDC);
}
// 绘制比例尺
if (m_ShowProportion)
{
DrawScaleBar(pDC);
}
CItemRectTracker::OnDraw(pXyDC, pDC);
}
int GetUnitIndex(LPCTSTR name);
//{
// CStringArray units;
// units.Add("公里");
// units.Add("千米");
// units.Add("千米");
// units.Add("米");
// units.Add(" (公里)");
// units.Add(" (千米)");
// units.Add(" (米)");
// int nSize = units.GetSize();
// for (int i = 0; i < nSize; i++) {
// if (units.GetAt(i).Compare(name) == 0) {
// return i;
// }
// }
// return -1;
//}
bool GetUnitString(int index, CString& str);
//{
// if (index < 0) {
// return "";
// }
// CStringArray units;
// units.Add("公里");
// units.Add("千米");
// units.Add("米");
// units.Add(" (公里)");
// units.Add(" (千米)");
// units.Add(" (米)");
// str = units.GetAt(index);
// return true;
//}
int NItem::CItemCopyAsImageEx::GetPropotionData(ProportionData * data)
{
data->x = m_Proportion.x0;
data->y = m_Proportion.y0;
data->ScaleLength = m_Proportion.m_dScaleLength;// *100;
DWORD nViewMode = m_Proportion.GetViewMode();
int nViewModeUI = 0;
if (nViewMode == CProportion::styleSimple) {
nViewModeUI = 0;
}
else if (nViewMode == CProportion::styleContemporaneity)
{
nViewModeUI = 1;
}
else if (nViewMode == CProportion::stylePopular)
{
nViewModeUI = 2;
}
data->ViewMode = nViewModeUI;
data->num = m_Proportion.num;
data->Unit = GetUnitIndex(m_Proportion.m_strUnit);
data->ColorR = GetRValue(m_Proportion.color);
data->ColorG = GetGValue(m_Proportion.color);
data->ColorB = GetBValue(m_Proportion.color);
data->TextScale = m_Proportion.m_dTextScale;
data->TextSpace = m_Proportion.m_dSpace;
DWORD nTextAlign = m_Proportion.GetAlignsH();
int nUIAlign = 1;
if (CTextFlags::alignLeft == nTextAlign) {
nUIAlign = 0;
}
else if (CTextFlags::alignCenterH == nTextAlign)
{
nUIAlign = 1;
}
else if (CTextFlags::alignRight == nTextAlign) {
nUIAlign = 2;
}
data->TextAlign = nUIAlign;
if (m_Proportion.m_size.cx <= 0 || m_Proportion.m_size.cy <= 0)
{
double dx = m_Proportion.m_dScaleLength*m_Proportion.m_dCoefficient;
data->TextHeight = dx * 0.2;// 0.1
data->TextWidth = data->TextHeight*0.4;
}
else {
data->TextWidth = m_Proportion.m_size.cx;
data->TextHeight = m_Proportion.m_size.cy;
}
return 1;
}
void NItem::CItemCopyAsImageEx::SetPropotionData(ProportionData * data) {
m_Proportion.x0 = data->x;
m_Proportion.y0 = data->y;
m_Proportion.m_dScaleLength = data->ScaleLength;// / 100;
switch (data->ViewMode)
{
case 0: m_Proportion.SetViewMode(CProportion::styleSimple);
break; //普通式
case 1: m_Proportion.SetViewMode(CProportion::styleContemporaneity);
break; //现代式
case 2: m_Proportion.SetViewMode(CProportion::stylePopular);
break; //流行式
}
m_Proportion.num = data->num;
GetUnitString(data->Unit, m_Proportion.m_strUnit);
m_Proportion.color = RGB(data->ColorR, data->ColorG, data->ColorB);
m_Proportion.m_dTextScale = data->TextScale;
m_Proportion.m_dSpace = data->TextSpace;
switch (data->TextAlign)
{
case 0:
m_Proportion.SetAlignsH(CTextFlags::alignLeft);
break;
case 1:
m_Proportion.SetAlignsH(CTextFlags::alignCenterH);
break;
case 2:
m_Proportion.SetAlignsH(CTextFlags::alignRight);
break;
}
m_Proportion.m_size.cx = data->TextWidth;
m_Proportion.m_size.cy = data->TextHeight;
}
void NItem::CItemCopyAsImageEx::TraceEnd()
{
m_tracker.m_rect.NormalizeRect();
m_coorRect = GetDC()->GetReal(m_tracker.m_rect);
}
void NItem::CItemCopyAsImageEx::OnLButtonDown(CDC *pDC, UINT nFlags, CPoint point, int vk) {
m_tracker.SetTrackStart(point);
}
int NItem::CItemCopyAsImageEx::OnMouseMove(CDC * pDC, UINT nFlags, CPoint point)
{
return 1;
}
void NItem::CItemCopyAsImageEx::OnLButtonUp(CDC *pDC, UINT nFlags, CPoint point, int vk)
{
TraceEnd();
}
int NItem::CItemCopyAsImageEx::HitTest(CPoint point)
{
//m_tracker.m_rect = GetDC()->GetScreen(m_coorRect);
return m_tracker.HitTest(point);
}
void NItem::CItemCopyAsImageEx::TrackHandle(int nHandle, CPoint point, CDC * pDCScreen)
{
m_tracker.Track(nHandle, point, m_bAllowInvert, pDCScreen);
}
bool NItem::CItemCopyAsImageEx::CopyRectToClipboard(double scaleFactor)
{
// 添加边界空白区
CRect8 rctTrue;
GetTrueRect(&rctTrue);
CPointList pts;
dfPoint pt;
pt.x0 = m_coorRect.left; pt.y0 = m_coorRect.bottom;
pts.AddTail(pt);
pt.x0 = m_coorRect.left; pt.y0 = m_coorRect.top;
pts.AddTail(pt);
pt.x0 = m_coorRect.right; pt.y0 = m_coorRect.top;
pts.AddTail(pt);
pt.x0 = m_coorRect.right; pt.y0 = m_coorRect.bottom;
pts.AddTail(pt);
pt.x0 = m_coorRect.left; pt.y0 = m_coorRect.bottom;
pts.AddTail(pt);
pt.x0 = rctTrue.left; pt.y0 = rctTrue.bottom;
pts.AddTail(pt);
pt.x0 = rctTrue.right; pt.y0 = rctTrue.bottom;
pts.AddTail(pt);
pt.x0 = rctTrue.right; pt.y0 = rctTrue.top;
pts.AddTail(pt);
pt.x0 = rctTrue.left; pt.y0 = rctTrue.top;
pts.AddTail(pt);
pt.x0 = rctTrue.left; pt.y0 = rctTrue.bottom;
pts.AddTail(pt);
CCurveEx* pc = new CCurveEx;
pc->SetPoints(pts, 2);
POSITION pos = this->AddElement(pc, DOUBLEFOX_CURVE, false, false);
this->GetDoc()->GetDraw()->SetElementLayer(pos, "__AttatchedElements");
COne* pOne = this->GetDoc()->GetDraw()->GetAt(pos);
//CHowToViewCurve hw;
CCurveProperties* pCurveProperty = new CCurveProperties();
pCurveProperty->color = RGB(255, 255, 255);
pCurveProperty->SetCurveType(PLINE_SOLID);
pCurveProperty->m_size.cx = 0;
//hw.Add(pCurveProperty);
pOne->HowToViewCurve = new CHowToViewCurve();
pOne->HowToViewCurve->Add(pCurveProperty);
if (m_ShowNetGrid) {
CGridding* pGrid = new CGridding();
*pGrid = m_Net;
CRect8 pRct;
pGrid->GetRange(pRct);
POSITION posNet = this->AddElement(pGrid, DOUBLEFOX_GRID, false, false);
this->GetDoc()->GetDraw()->SetElementLayer(posNet, "__AttatchedElements");
}
if (m_ShowProportion) {
CProportion* pProportion = new CProportion();
*pProportion = m_Proportion;
CRect8 pRct;
pProportion->GetRange(pRct);
POSITION posProp = this->AddElement(pProportion, DOUBLEFOX_PROPORTION, false, false);
this->GetDoc()->GetDraw()->SetElementLayer(posProp, "__AttatchedElements");
}
CopyToClipboard(rctTrue, scaleFactor);
// 删除边界空白区
GetDoc()->GetDraw()->RemoveLayer("__AttatchedElements", 0, 1);
return true;
}
void NItem::CItemCopyAsImageEx::CopyToClipboard(CRect8& rect, double scaleFactor)
{
CXyDC* pXyDc = GetDC();
CRect rt = pXyDc->GetScreen(rect);
if (rt.IsRectEmpty()) return;
//
pXyDc->Reduce(scaleFactor);
CRect rtScale = pXyDc->GetScreen(rect);
double dx = rect.left - pXyDc->left;
double dy = rect.top - pXyDc->top;
pXyDc->OffsetRect(dx, dy);
CItemExportFile ef(GetDoc());
CMemoryDC *pmdc = ef.ExportImage(rtScale.Size(), 24);
if (pmdc)
{
pmdc->CopyToClipboard();
delete pmdc;
}
pXyDc->OffsetRect(-dx, -dy);
pXyDc->Reduce(1.0/scaleFactor);
}