📄 cube3dview.cpp
字号:
// Cube3dView.cpp : implementation of the CCube3dView class
//
#include "stdafx.h"
#include "Cube3d.h"
#include "Cube3dDoc.h"
#include "Cube3dView.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
#include "TypedStack.h"
#include "Cube.h"
#include "PRender.h"
/////////////////////////////////////////////////////////////////////////////
// CCube3dView
IMPLEMENT_DYNCREATE(CCube3dView, CView)
BEGIN_MESSAGE_MAP(CCube3dView, CView)
//{{AFX_MSG_MAP(CCube3dView)
// NOTE - the ClassWizard will add and remove mapping macros here.
// DO NOT EDIT what you see in these blocks of generated code!
//}}AFX_MSG_MAP
END_MESSAGE_MAP()
/////////////////////////////////////////////////////////////////////////////
// CCube3dView construction/destruction
CCube3dView::CCube3dView()
{
}
CCube3dView::~CCube3dView()
{
}
BOOL CCube3dView::PreCreateWindow(CREATESTRUCT& cs)
{
// TODO: Modify the Window class or styles here by modifying
// the CREATESTRUCT cs
return CView::PreCreateWindow(cs);
}
/////////////////////////////////////////////////////////////////////////////
// CCube3dView drawing
void CCube3dView::OnDraw(CDC* pDC)
{
// TODO: add draw code for native data here
//第一步, 创建一个内存设备对象
//获取客户区大小
CRect rect;
GetClientRect(&rect);
int nClientWidth = rect.Width();
int nClientHeight = rect.Height();
//建立一个内存设备
//内存设备及其初始化
CDC memDC;
memDC.CreateCompatibleDC(pDC);
CBitmap bitmap;
bitmap.CreateCompatibleBitmap(pDC, nClientWidth, nClientHeight);
CBitmap* pOldBitmap = memDC.SelectObject(&bitmap);
CBrush* pBrush = new CBrush(RGB(0, 0, 0));
memDC.FillRect(rect, pBrush);
delete pBrush;
//绘制立方体
//第二步, 申明一个立方体对象, 并且申明它的颜色需要外部指定
CCube* pCube = new CCube(0.8f, 1.3f, 0.8f);
pCube->SetAutoColorProperty(FALSE);
//第三步, 设置绘制属性
//要注意, 我们这里采用的是手动的方法设置颜色
//因而, 我们可以把这一步放在几何之前.从而方便后面的克隆
//设置顶点颜色
FLOATCOLORRGBA clrVertex[8] = {
{0.0f, 1.0f, 0.0f, 1.0f}, {0.0f, 1.0f, 1.0f, 1.0f},
{0.0f, 0.0f, 0.0f, 1.0f}, {0.0f, 0.0f, 1.0f, 1.0f},
{1.0f, 0.0f, 0.0f, 1.0f}, {1.0f, 1.0f, 0.0f, 1.0f},
{1.0f, 1.0f, 1.0f, 1.0f}, {1.0f, 0.0f, 1.0f, 1.0f}};
for(int i = 0; i < 8; i++)
pCube->SetVertexColor(i, clrVertex[i]);
//设置边颜色
for(i = 0; i < 12; i++)
pCube->SetEdgeColor(i, 1.0f, 0.0f, 0.0f);
//设置小面颜色
FLOATCOLORRGBA clrFacet[6] = {
{1.0f, 1.0f, 1.0f, 1.0f}, {1.0f, 1.0f, 1.0f, 1.0f},
{0.38f, 0.38f, 0.38f, 1.0f}, {0.8f, 0.8f, 0.8f, 1.0f},
{0.38f, 0.38f, 0.38f, 1.0f}, {0.8f, 0.8f, 0.8f, 1.0f}};
for(i = 0; i < 6; i++)
pCube->SetFacetColor(i, clrFacet[i]);
//第四步, 组织场景, 进行几何变换
//构造一个矩阵堆栈
CTypedStack<CMatrix3d> matrixStack;
//变换矩阵
CMatrix3d mGeometry;
//压入单位矩阵(起示例作用)
matrixStack.Push(mGeometry);
mGeometry.RotateY(25.0f);
mGeometry.RotateX(35.0f);
mGeometry.RotateZ(-15.0f);
mGeometry.Translate(2.0f, 0.0f, 0.0f);
matrixStack.Push(mGeometry);
mGeometry.Translate(-1.3f, 0.0f, 0.0f);
matrixStack.Push(mGeometry);
mGeometry.Translate(-1.3f, 0.0f, 0.0f);
matrixStack.Push(mGeometry);
//申明两个克隆体, 注意, 克隆时, 连位置一起克隆
//此时, pCube的位置在原始位置
CCube* pCube1 = pCube->Clone();
CCube* pCube2 = pCube->Clone();
//弹出
pCube2->Transform(matrixStack.Pop());
pCube1->Transform(matrixStack.Pop());
pCube->Transform(matrixStack.Pop());
//弹出单位矩阵
matrixStack.Pop();
//第五步, 设置观察点和取景器(置于 Z 轴上)
VERTEX3D viewer = {0.0f, 0.0f, 8.0f};
//视口变换中进行放大处理, 屏幕位置距离视点100个单位;
//透视中心(屏幕坐标)为(180, 150)
VIEWFINDER viewFinder = {100.0f, 8.0f, 8.0f, {180, 150}};
//第五步, 着色
CPRender renderer;
//线框模型
renderer.Render(&memDC, pCube, viewer, viewFinder, G3D_RENDER_WIRE);
//刻面模型
renderer.Render(&memDC, pCube1, viewer, viewFinder, G3D_RENDER_FLAT);
//光滑明暗模型
renderer.Render(&memDC, pCube2, viewer, viewFinder, G3D_RENDER_GOURAUD_SMOOTH);
//第七步, 显示结果
pDC->BitBlt(0, 0, nClientWidth, nClientHeight, &memDC, 0, 0, SRCCOPY);
//第八步, 复原CDC属性
memDC.SelectObject(pOldBitmap);
bitmap.DeleteObject();
delete pCube;
delete pCube1;
delete pCube2;
}
/////////////////////////////////////////////////////////////////////////////
// CCube3dView diagnostics
#ifdef _DEBUG
void CCube3dView::AssertValid() const
{
CView::AssertValid();
}
void CCube3dView::Dump(CDumpContext& dc) const
{
CView::Dump(dc);
}
CCube3dDoc* CCube3dView::GetDocument() // non-debug version is inline
{
ASSERT(m_pDocument->IsKindOf(RUNTIME_CLASS(CCube3dDoc)));
return (CCube3dDoc*)m_pDocument;
}
#endif //_DEBUG
/////////////////////////////////////////////////////////////////////////////
// CCube3dView message handlers
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -