Beispiel #1
0
HRESULT Scene::CreateMouthGeometry()
{
	HRESULT hr = S_OK;
	//mouth
	hr = m_pFactory->CreatePathGeometry(&m_pMouthGeometry);
	if (SUCCEEDED(hr))
	{
		ID2D1GeometrySink *pSink = NULL;
		hr = m_pMouthGeometry->Open(&pSink);
		if (SUCCEEDED(hr))
		{
			pSink->SetFillMode(D2D1_FILL_MODE_WINDING);

			pSink->BeginFigure(
				D2D1::Point2F(m_ellipse.point.x, m_ellipse.point.y),
				D2D1_FIGURE_BEGIN_FILLED
				);
			D2D1_POINT_2F points[3] = {
				D2D1::Point2F(m_ellipse.point.x + m_ellipse.radiusX, m_ellipse.point.y - 10),
				D2D1::Point2F(m_ellipse.point.x + m_ellipse.radiusX, m_ellipse.point.y + 10),
				
				D2D1::Point2F(m_ellipse.point.x, m_ellipse.point.y),
			};
			pSink->AddLines(points, ARRAYSIZE(points));
			pSink->EndFigure(D2D1_FIGURE_END_CLOSED);

		}
		hr = pSink->Close();

		SafeRelease(&pSink);
		return hr;
	}
}
Beispiel #2
0
/// <summary>
/// Initializes a new instance of the <see cref="Polygon"/> class.
/// </summary>
/// <param name="">The .</param>
RubyGM::Drawable::Polygon::Polygon(const PolygonStatus& ps) noexcept : 
Super(ps) {
    assert(m_pGiGeometry == nullptr);
    assert(ps.points && ps.count >= 3); 
    // 初始化
    ID2D1PathGeometry* path = nullptr;
    ID2D1GeometrySink* sink = nullptr;
    // 创建路径几何
    auto hr = Bridge::CreatePathGeometry(path);
    // 打开路径记录
    if (SUCCEEDED(hr)) {
        hr = path->Open(&sink);
    }
    // 填充路径
    if (SUCCEEDED(hr)) {
        auto points = impl::d2d(ps.points);
        sink->SetFillMode(D2D1_FILL_MODE(ps.fill_rule));
        sink->BeginFigure(*points, D2D1_FIGURE_BEGIN_FILLED);
        sink->AddLines(points + 1, ps.count - 1);
        sink->EndFigure(D2D1_FIGURE_END_CLOSED);
        hr = sink->Close();
    }
    // 错误代码
    if (FAILED(hr)) Game::SetLastErrorCode(hr);
    RubyGM::SafeRelease(sink);
    // 数据转换
    auto gi = static_cast<ID2D1Geometry*>(path);
    m_pGiGeometry = static_cast<IGMGeometry*>(gi);
}
RenderableGrid::RenderableGrid(Direct2D1& _d2d1, IJSON& _parameters)
:	Renderable(_d2d1, _parameters),
	m_geometry(NULL),
	m_tgeometry(NULL)
{
	IJSON& params = *_parameters[L"parameters"];
	D2D1_SIZE_F size, steps;
	size.width = (*params[L"size"])[0]->AsNumber();
	size.height = (*params[L"size"])[1]->AsNumber();
	steps.width = (*params[L"steps"])[0]->AsNumber();
	steps.height = (*params[L"steps"])[1]->AsNumber();

	if (SUCCEEDED(this->m_d2d1.D2D1().CreatePathGeometry(&this->m_geometry)))
	{
		ID2D1GeometrySink *pSink = NULL;
		if (SUCCEEDED(this->m_geometry->Open(&pSink)))
		{
			D2D1_POINT_2F p1, p2;

			pSink->SetFillMode(D2D1_FILL_MODE_WINDING);

			p1.y = -size.height / 2.0f;
			p2.y = size.height / 2.0f;
			for (float x = -size.width / 2.0f ; (size.width / 2.0f) >= x ; x += steps.width)
			{
				p1.x = x;
				p2.x = x;
				pSink->BeginFigure(p1, D2D1_FIGURE_BEGIN_HOLLOW);
				pSink->AddLine(p2);
				pSink->EndFigure(D2D1_FIGURE_END_OPEN);
			}

			p1.x = -size.width / 2.0f;
			p2.x = size.width / 2.0f;
			for (float y = -size.height / 2.0f ; (size.height / 2.0f) >= y ; y += steps.height)
			{
				p1.y = y;
				p2.y = y;
				pSink->BeginFigure(p1, D2D1_FIGURE_BEGIN_HOLLOW);
				pSink->AddLine(p2);
				pSink->EndFigure(D2D1_FIGURE_END_OPEN);
			}

			pSink->Close();
			pSink->Release();
		}
	}
}
Beispiel #4
0
Home::Home(float xPos, float yPos, ID2D1Factory *pID2D1Factory) : Actor(xPos, yPos)
{
	r = 0.0f;
	g = 1.0f;
	b = 0.0f;
	a = 1.0f;

	HRESULT hr = pID2D1Factory->CreatePathGeometry(&pHomeGeometry);
	if (SUCCEEDED(hr))
	{
		ID2D1GeometrySink *pSink = NULL;

		hr = pHomeGeometry->Open(&pSink);
		if (SUCCEEDED(hr))
		{
			pSink->SetFillMode(D2D1_FILL_MODE_WINDING);

			pSink->BeginFigure(
				D2D1::Point2F(25, -25),
				D2D1_FIGURE_BEGIN_FILLED
				);
			D2D1_POINT_2F points[] = {
				D2D1::Point2F(25, 25),
				D2D1::Point2F(-25, 25),
				D2D1::Point2F(-25, -25)
			};
			pSink->AddLines(points, ARRAYSIZE(points));
			pSink->EndFigure(D2D1_FIGURE_END_CLOSED);
		}
		hr = pSink->Close();
		pSink->Release();

	}

	D2D1_MATRIX_3X2_F mov;
	mov = D2D1::Matrix3x2F::Translation(
		D2D1::SizeF(x, y)
		);

	D2D1_MATRIX_3X2_F transform = mov;
	hr = pID2D1Factory->CreateTransformedGeometry(
		pHomeGeometry,
		&transform,
		&pTransformed
		);
}
void VGraphicPath::Begin()
{
#if ENABLE_D2D
	//start to populate geometry
	if (fGeomSink)
		return;
	if (fPathD2D == NULL)
		return;

	ID2D1PathGeometry *thisPath = NULL;
	if (FAILED(fPathD2D->QueryInterface( __uuidof(ID2D1PathGeometry), (void **)&thisPath)))
		return; //no more a ID2D1PathGeometry so skip
	ID2D1GeometrySink *thisGeomSink;
	if (SUCCEEDED(thisPath->Open(&thisGeomSink)))
	{
		fGeomSink = thisGeomSink;
		thisGeomSink->SetFillMode( fFillMode == FILLRULE_EVENODD ? D2D1_FILL_MODE_ALTERNATE : D2D1_FILL_MODE_WINDING);
		fFigureIsClosed = true;
	}
	thisPath->Release();
#endif
}
HRESULT SaveToImageFile()
{
    HRESULT hr = S_OK;


    //
    // Create Factories
    //

    IWICImagingFactory *pWICFactory = NULL;
    ID2D1Factory *pD2DFactory = NULL;
    IDWriteFactory *pDWriteFactory = NULL;
    IWICBitmap *pWICBitmap = NULL;
    ID2D1RenderTarget *pRT = NULL;
    IDWriteTextFormat *pTextFormat = NULL;
    ID2D1PathGeometry *pPathGeometry = NULL;
    ID2D1GeometrySink *pSink = NULL;
    ID2D1GradientStopCollection *pGradientStops = NULL;
    ID2D1LinearGradientBrush *pLGBrush = NULL;
    ID2D1SolidColorBrush *pBlackBrush = NULL;
    IWICBitmapEncoder *pEncoder = NULL;
    IWICBitmapFrameEncode *pFrameEncode = NULL;
    IWICStream *pStream = NULL;

    hr = CoCreateInstance(
        CLSID_WICImagingFactory,
        NULL,
        CLSCTX_INPROC_SERVER,
        IID_IWICImagingFactory,
        reinterpret_cast<void **>(&pWICFactory)
        );

    if (SUCCEEDED(hr))
    {
        hr = D2D1CreateFactory(D2D1_FACTORY_TYPE_SINGLE_THREADED, &pD2DFactory);
    }

    if (SUCCEEDED(hr))
    {
        hr = DWriteCreateFactory(
            DWRITE_FACTORY_TYPE_SHARED,
            __uuidof(pDWriteFactory),
            reinterpret_cast<IUnknown **>(&pDWriteFactory)
            );
    }

    //
    // Create IWICBitmap and RT
    //

    static const UINT sc_bitmapWidth = 640;
    static const UINT sc_bitmapHeight = 480;
    if (SUCCEEDED(hr))
    {
        hr = pWICFactory->CreateBitmap(
            sc_bitmapWidth,
            sc_bitmapHeight,
            GUID_WICPixelFormat32bppBGR,
            WICBitmapCacheOnLoad,
            &pWICBitmap
            );
    }

    if (SUCCEEDED(hr))
    {
        hr = pD2DFactory->CreateWicBitmapRenderTarget(
            pWICBitmap,
            D2D1::RenderTargetProperties(),
            &pRT
            );
    }

    if (SUCCEEDED(hr))
    {
        //
        // Create text format
        //

        static const WCHAR sc_fontName[] = L"Calibri";
        static const FLOAT sc_fontSize = 50;

        hr = pDWriteFactory->CreateTextFormat(
            sc_fontName,
            NULL,
            DWRITE_FONT_WEIGHT_NORMAL,
            DWRITE_FONT_STYLE_NORMAL,
            DWRITE_FONT_STRETCH_NORMAL,
            sc_fontSize,
            L"", //locale
            &pTextFormat
            );
    }
    if (SUCCEEDED(hr))
    {
        pTextFormat->SetTextAlignment(DWRITE_TEXT_ALIGNMENT_CENTER);

        pTextFormat->SetParagraphAlignment(DWRITE_PARAGRAPH_ALIGNMENT_CENTER);

        //
        // Create a path geometry representing an hour glass
        //

        hr = pD2DFactory->CreatePathGeometry(&pPathGeometry);
    }
    if (SUCCEEDED(hr))
    {
        hr = pPathGeometry->Open(&pSink);
    }
    if (SUCCEEDED(hr))
    {
        pSink->SetFillMode(D2D1_FILL_MODE_ALTERNATE);

        pSink->BeginFigure(
            D2D1::Point2F(0, 0),
            D2D1_FIGURE_BEGIN_FILLED
            );

        pSink->AddLine(D2D1::Point2F(200, 0));

        pSink->AddBezier(
            D2D1::BezierSegment(
                D2D1::Point2F(150, 50),
                D2D1::Point2F(150, 150),
                D2D1::Point2F(200, 200))
            );

        pSink->AddLine(D2D1::Point2F(0, 200));

        pSink->AddBezier(
            D2D1::BezierSegment(
                D2D1::Point2F(50, 150),
                D2D1::Point2F(50, 50),
                D2D1::Point2F(0, 0))
            );

        pSink->EndFigure(D2D1_FIGURE_END_CLOSED);

        hr = pSink->Close();
    }
    if (SUCCEEDED(hr))
    {
        //
        // Create a linear-gradient brush
        //

        static const D2D1_GRADIENT_STOP stops[] =
        {
            {   0.f,  { 0.f, 1.f, 1.f, 1.f }  },
            {   1.f,  { 0.f, 0.f, 1.f, 1.f }  },
        };

        hr = pRT->CreateGradientStopCollection(
            stops,
            ARRAYSIZE(stops),
            &pGradientStops
            );
    }
    if (SUCCEEDED(hr))
    {
        hr = pRT->CreateLinearGradientBrush(
            D2D1::LinearGradientBrushProperties(
                D2D1::Point2F(100, 0),
                D2D1::Point2F(100, 200)),
            D2D1::BrushProperties(),
            pGradientStops,
            &pLGBrush
            );
    }
    if (SUCCEEDED(hr))
    {
        hr = pRT->CreateSolidColorBrush(
            D2D1::ColorF(D2D1::ColorF::Black),
            &pBlackBrush
            );
    }
    if (SUCCEEDED(hr))
    {
        //
        // Render into the bitmap
        //

        pRT->BeginDraw();

        pRT->Clear(D2D1::ColorF(D2D1::ColorF::White));

        D2D1_SIZE_F rtSize = pRT->GetSize();

        // Set the world transform to a 45 degree rotation at the center of the render target
        // and write "Hello, World".
        pRT->SetTransform(
            D2D1::Matrix3x2F::Rotation(
                45,
                D2D1::Point2F(
                    rtSize.width / 2,
                    rtSize.height / 2))
                );

        static const WCHAR sc_helloWorld[] = L"Hello, World!";
        pRT->DrawText(
            sc_helloWorld,
            ARRAYSIZE(sc_helloWorld) - 1,
            pTextFormat,
            D2D1::RectF(0, 0, rtSize.width, rtSize.height),
            pBlackBrush);

        //
        // Reset back to the identity transform
        //
        pRT->SetTransform(D2D1::Matrix3x2F::Translation(0, rtSize.height - 200));

        pRT->FillGeometry(pPathGeometry, pLGBrush);

        pRT->SetTransform(D2D1::Matrix3x2F::Translation(rtSize.width - 200, 0));

        pRT->FillGeometry(pPathGeometry, pLGBrush);

        hr = pRT->EndDraw();
    }
    if (SUCCEEDED(hr))
    {

        //
        // Save image to file
        //

        hr = pWICFactory->CreateStream(&pStream);
    }

    WICPixelFormatGUID format = GUID_WICPixelFormatDontCare;
    if (SUCCEEDED(hr))
    {
        static const WCHAR filename[] = L"output.png";
        hr = pStream->InitializeFromFilename(filename, GENERIC_WRITE);
    }
    if (SUCCEEDED(hr))
    {
        hr = pWICFactory->CreateEncoder(GUID_ContainerFormatPng, NULL, &pEncoder);
    }
    if (SUCCEEDED(hr))
    {
        hr = pEncoder->Initialize(pStream, WICBitmapEncoderNoCache);
    }
    if (SUCCEEDED(hr))
    {
        hr = pEncoder->CreateNewFrame(&pFrameEncode, NULL);
    }
    if (SUCCEEDED(hr))
    {
        hr = pFrameEncode->Initialize(NULL);
    }
    if (SUCCEEDED(hr))
    {
        hr = pFrameEncode->SetSize(sc_bitmapWidth, sc_bitmapHeight);
    }
    if (SUCCEEDED(hr))
    {
        hr = pFrameEncode->SetPixelFormat(&format);
    }
    if (SUCCEEDED(hr))
    {
        hr = pFrameEncode->WriteSource(pWICBitmap, NULL);
    }
    if (SUCCEEDED(hr))
    {
        hr = pFrameEncode->Commit();
    }
    if (SUCCEEDED(hr))
    {
        hr = pEncoder->Commit();
    }

    SafeRelease(&pWICFactory);
    SafeRelease(&pD2DFactory);
    SafeRelease(&pDWriteFactory);
    SafeRelease(&pWICBitmap);
    SafeRelease(&pRT);
    SafeRelease(&pTextFormat);
    SafeRelease(&pPathGeometry);
    SafeRelease(&pSink);
    SafeRelease(&pGradientStops);
    SafeRelease(&pLGBrush);
    SafeRelease(&pBlackBrush);
    SafeRelease(&pEncoder);
    SafeRelease(&pFrameEncode);
    SafeRelease(&pStream);

    return hr;
}
Beispiel #7
0
 void STDMETHODCALLTYPE SetFillMode(D2D1_FILL_MODE fillMode) 
 {
     if( m_BaseSink )
         m_BaseSink->SetFillMode(fillMode);
 }
// Create device-independent resources
HRESULT DemoApp::CreateDeviceIndependentResources()
{
	static const WCHAR msc_fontName[] = L"Verdana";
	static const FLOAT msc_fontSize = 50;
	HRESULT hr;
	ID2D1GeometrySink *pSink = NULL;

	// Create a Direct2D factory
	hr = D2D1CreateFactory(D2D1_FACTORY_TYPE_SINGLE_THREADED, &m_pD2DFactory);
	if (SUCCEEDED(hr))
	{
		// Create WIC factory
		hr = CoCreateInstance(
			CLSID_WICImagingFactory,
			NULL,
			CLSCTX_INPROC_SERVER,
			IID_IWICImagingFactory,
			reinterpret_cast<void **>(&m_pWICFactory));
	}
	if (SUCCEEDED(hr))
	{
		// Create a DirectWrite factory
		hr = DWriteCreateFactory(
			DWRITE_FACTORY_TYPE_SHARED,
			__uuidof(m_pDWriteFactory),
			reinterpret_cast<IUnknown **>(&m_pDWriteFactory));
	}
	if (SUCCEEDED(hr))
	{
		// Create a DirectWrite text format object
		hr = m_pDWriteFactory->CreateTextFormat(
			msc_fontName,
			NULL,
			DWRITE_FONT_WEIGHT_NORMAL,
			DWRITE_FONT_STYLE_NORMAL,
			DWRITE_FONT_STRETCH_NORMAL,
			msc_fontSize,
			L"",
			&m_pTextFormat);
	}
	if (SUCCEEDED(hr))
	{
		// center the text horizontally and vertically
		m_pTextFormat->SetTextAlignment(DWRITE_TEXT_ALIGNMENT_CENTER);
		m_pTextFormat->SetParagraphAlignment(DWRITE_PARAGRAPH_ALIGNMENT_CENTER);

		// Create a path geometry
		hr = m_pD2DFactory->CreatePathGeometry(&m_pPathGeometry);
	}
	if (SUCCEEDED(hr))
	{
		// Use the geometry sink to write to the path geometry
		hr = m_pPathGeometry->Open(&pSink);
	}
	if (SUCCEEDED(hr))
	{
		pSink->SetFillMode(D2D1_FILL_MODE_ALTERNATE);

		pSink->BeginFigure(D2D1::Point2F(0, 0), D2D1_FIGURE_BEGIN_FILLED);
		pSink->AddLine(D2D1::Point2F(200, 0));
		pSink->AddBezier(
			D2D1::BezierSegment(
				D2D1::Point2F(150, 50),
				D2D1::Point2F(150, 150),
				D2D1::Point2F(200, 200)));
		pSink->AddLine(D2D1::Point2F(0, 200));
		pSink->AddBezier(
			D2D1::BezierSegment(
				D2D1::Point2F(50, 150),
				D2D1::Point2F(50, 50),
				D2D1::Point2F(0, 0)));
		pSink->EndFigure(D2D1_FIGURE_END_CLOSED);
		hr = pSink->Close();
	}
	SafeRelease(&pSink);
	return hr;
}
Beispiel #9
0
//-----------------------------------------------------------------------------
ID2D1PathGeometry* D2DGraphicsPath::getPath (int32_t fillMode)
{
	if (path == 0 || fillMode != currentPathFillMode)
	{
		dirty ();
		if (!SUCCEEDED (getD2DFactory ()->CreatePathGeometry (&path)))
			return 0;
		if (fillMode == -1)
			fillMode = 0;
		currentPathFillMode = fillMode;
		
		ID2D1GeometrySink* sink = 0;
		if (!SUCCEEDED (path->Open (&sink)))
		{
			path->Release ();
			path = 0;
			return 0;
		}

		sink->SetFillMode ((D2D1_FILL_MODE)fillMode);

		bool figureOpen = false;
		CPoint lastPos;
		for (ElementList::const_iterator it = elements.begin (); it != elements.end (); it++)
		{
			Element e = (*it);
			switch (e.type)
			{
				case Element::kArc:
				{
					bool clockwise = e.instruction.arc.clockwise;
					double startAngle = e.instruction.arc.startAngle;
					double endAngle = e.instruction.arc.endAngle;
					CRect o_r (e.instruction.arc.rect.left, e.instruction.arc.rect.top, e.instruction.arc.rect.right, e.instruction.arc.rect.bottom);
					CRect r (o_r);
					o_r.originize ();
					CPoint center = o_r.getCenter ();
					CPoint start;
					start.x = r.left + center.x + center.x * cos (radians (startAngle));
					start.y = r.top + center.y + center.y * sin (radians (startAngle));
					if (!figureOpen)
					{
						sink->BeginFigure (makeD2DPoint (start), D2D1_FIGURE_BEGIN_FILLED);
						figureOpen = true;
					}
					else if (lastPos != start)
					{
						sink->AddLine (makeD2DPoint (start));
					}

					double sweepangle = endAngle - startAngle;
					if (clockwise) {
						// sweepangle positive
						while (sweepangle < 0.0)
							sweepangle += 360.0;
						while (sweepangle > 360.0)
							sweepangle -= 360.0;
					} else {
						// sweepangle negative
						while (sweepangle > 0.0)
							sweepangle -= 360.0;
						while (sweepangle < -360.0)
							sweepangle += 360.0;
					}

					CPoint endPoint;
					endPoint.x = r.left + center.x + center.x * cos (radians (endAngle));
					endPoint.y = r.top + center.y + center.y * sin (radians (endAngle));

					D2D1_ARC_SEGMENT arc;
					arc.size = makeD2DSize (r.getWidth ()/2., r.getHeight ()/2.);
					arc.rotationAngle = 0;
					arc.sweepDirection = clockwise ? D2D1_SWEEP_DIRECTION_CLOCKWISE : D2D1_SWEEP_DIRECTION_COUNTER_CLOCKWISE;
					arc.point = makeD2DPoint (endPoint);
					arc.arcSize = fabs(sweepangle) <= 180. ? D2D1_ARC_SIZE_SMALL : D2D1_ARC_SIZE_LARGE;
					sink->AddArc (arc);
					lastPos = endPoint;
					break;
				}
				case Element::kEllipse:
				{
					CRect r (e.instruction.rect.left, e.instruction.rect.top, e.instruction.rect.right, e.instruction.rect.bottom);
					CPoint top (r.getTopLeft ());
					top.x += r.getWidth () / 2.;
					CPoint bottom (r.getBottomLeft ());
					bottom.x += r.getWidth () / 2.;
					if (figureOpen && lastPos != CPoint (e.instruction.rect.left, e.instruction.rect.top))
					{
						sink->EndFigure (D2D1_FIGURE_END_OPEN);
						figureOpen = false;
					}
					if (!figureOpen)
					{
						sink->BeginFigure (makeD2DPoint (top), D2D1_FIGURE_BEGIN_FILLED);
						figureOpen = true;
					}
					D2D1_ARC_SEGMENT arc = D2D1::ArcSegment (makeD2DPoint (bottom), D2D1::SizeF ((FLOAT)r.getWidth ()/2.f, (FLOAT)r.getHeight ()/2.f), 180.f, D2D1_SWEEP_DIRECTION_CLOCKWISE, D2D1_ARC_SIZE_SMALL);
					sink->AddArc (arc);
					arc.point = makeD2DPoint (top);
					sink->AddArc (arc);
					lastPos = top;
					break;
				}
				case Element::kRect:
				{
					D2D1_POINT_2F points[4] = {
						{(FLOAT)e.instruction.rect.right, (FLOAT)e.instruction.rect.top},
						{(FLOAT)e.instruction.rect.right, (FLOAT)e.instruction.rect.bottom},
						{(FLOAT)e.instruction.rect.left, (FLOAT)e.instruction.rect.bottom},
						{(FLOAT)e.instruction.rect.left, (FLOAT)e.instruction.rect.top}
					};
					if (figureOpen && lastPos != CPoint (e.instruction.rect.left, e.instruction.rect.top))
					{
						sink->EndFigure (D2D1_FIGURE_END_OPEN);
						figureOpen = false;
					}
					if (figureOpen == false)
					{
						sink->BeginFigure (points[3], D2D1_FIGURE_BEGIN_FILLED);
						figureOpen = true;
					}
					sink->AddLine (points[0]);
					sink->AddLine (points[1]);
					sink->AddLine (points[2]);
					sink->AddLine (points[3]);
					lastPos = CPoint (e.instruction.rect.left, e.instruction.rect.top);
					break;
				}
				case Element::kLine:
				{
					if (figureOpen)
					{
						D2D1_POINT_2F end = {(FLOAT)e.instruction.point.x, (FLOAT)e.instruction.point.y};
						sink->AddLine (end);
						lastPos = CPoint (e.instruction.point.x, e.instruction.point.y);
					}
					break;
				}
				case Element::kBezierCurve:
				{
					if (figureOpen)
					{
						D2D1_POINT_2F control1 = {(FLOAT)e.instruction.curve.control1.x, (FLOAT)e.instruction.curve.control1.y};
						D2D1_POINT_2F control2 = {(FLOAT)e.instruction.curve.control2.x, (FLOAT)e.instruction.curve.control2.y};
						D2D1_POINT_2F end = {(FLOAT)e.instruction.curve.end.x, (FLOAT)e.instruction.curve.end.y};
						D2D1_BEZIER_SEGMENT bezier = D2D1::BezierSegment (control1, control2, end);
						sink->AddBezier (bezier);
						lastPos = CPoint (e.instruction.curve.end.x, e.instruction.curve.end.y);
					}
					break;
				}
				case Element::kBeginSubpath:
				{
					if (figureOpen)
						sink->EndFigure (D2D1_FIGURE_END_OPEN);
					D2D1_POINT_2F start = {(FLOAT)e.instruction.point.x, (FLOAT)e.instruction.point.y};
					sink->BeginFigure (start, D2D1_FIGURE_BEGIN_FILLED);
					figureOpen = true;
					lastPos = CPoint (e.instruction.point.x, e.instruction.point.y);
					break;
				}
				case Element::kCloseSubpath:
				{
					if (figureOpen)
					{
						sink->EndFigure (D2D1_FIGURE_END_CLOSED);
						figureOpen = false;
					}
					break;
				}
			}
		}
		if (figureOpen)
			sink->EndFigure (D2D1_FIGURE_END_OPEN);
		HRESULT res = sink->Close ();
		if (!SUCCEEDED (res))
		{
			path->Release ();
			path = 0;
		}
		sink->Release ();
	}
	return path;
}
Beispiel #10
0
VOID CreateD2DResource(HWND hWnd)
{
	// This function was called in the DrawRectangle function which in turn called to response the
	// WM_PAINT Message, to avoid creating resource every time, we test the pointer to g_pRenderTarget
	// If the resource already create, skip the function
	if (!g_pRenderTarget)
	{
		HRESULT hr = D2D1CreateFactory(D2D1_FACTORY_TYPE_SINGLE_THREADED, &g_pD2DFactory) ;
		if (FAILED(hr))
		{
			MessageBox(hWnd, "Create D2D factory failed!", "Error", 0) ;
			return ;
		}

		// Obtain the size of the drawing area
		RECT rc ;		
		GetClientRect(hWnd, &rc) ;

		// Create a Direct2D render target
		hr = g_pD2DFactory->CreateHwndRenderTarget(
			D2D1::RenderTargetProperties(),
			D2D1::HwndRenderTargetProperties(
			hWnd, 
			D2D1::SizeU(rc.right - rc.left,rc.bottom - rc.top)
			), 
			&g_pRenderTarget
			) ;
		if (FAILED(hr))
		{
			MessageBox(hWnd, "Create render target failed!", "Error", 0) ;
			return ;
		}

		// Create a brush
		hr = g_pRenderTarget->CreateSolidColorBrush(
			D2D1::ColorF(D2D1::ColorF::Black),
			&g_pSceneBrush
			) ;
		if (FAILED(hr))
		{
			MessageBox(hWnd, "Create brush failed!", "Error", 0) ;
			return ;
		}

		// Create left mountain geometry
		hr = g_pD2DFactory->CreatePathGeometry(&g_pLeftMountainGeometry) ;
		if (SUCCEEDED(hr))
		{
			ID2D1GeometrySink *pSink = NULL;

			hr = g_pLeftMountainGeometry->Open(&pSink);
			if (SUCCEEDED(hr))
			{
				pSink->SetFillMode(D2D1_FILL_MODE_WINDING);

				pSink->BeginFigure(
					D2D1::Point2F(346,255),
					D2D1_FIGURE_BEGIN_FILLED
					);
				D2D1_POINT_2F points[5] = {
					D2D1::Point2F(267, 177),
					D2D1::Point2F(236, 192),
					D2D1::Point2F(212, 160),
					D2D1::Point2F(156, 255),
					D2D1::Point2F(346, 255), 
				};
				pSink->AddLines(points, ARRAYSIZE(points));
				pSink->EndFigure(D2D1_FIGURE_END_CLOSED);
			}
			pSink->Close() ;

			SAFE_RELEASE(pSink) ;
		}
		
		// Create right mountain geometry
		hr = g_pD2DFactory->CreatePathGeometry(&g_pRightMountainGeometry) ;
		if (SUCCEEDED(hr))
		{
			ID2D1GeometrySink *pSink = NULL;

			hr = g_pRightMountainGeometry->Open(&pSink);
			if (SUCCEEDED(hr))
			{
				pSink->SetFillMode(D2D1_FILL_MODE_WINDING);

				pSink->BeginFigure(
					D2D1::Point2F(575,263),
					D2D1_FIGURE_BEGIN_FILLED
					);
				D2D1_POINT_2F points[] = {
					D2D1::Point2F(481, 146),
					D2D1::Point2F(449, 181),
					D2D1::Point2F(433, 159),
					D2D1::Point2F(401, 214),
					D2D1::Point2F(381, 199), 
					D2D1::Point2F(323, 263), 
					D2D1::Point2F(575, 263)
				};
				pSink->AddLines(points, ARRAYSIZE(points));
				pSink->EndFigure(D2D1_FIGURE_END_CLOSED);
			}
			hr = pSink->Close();

			SAFE_RELEASE(pSink);

		}
		// Create sun geometry
		hr = g_pD2DFactory->CreatePathGeometry(&g_pSunGeometry) ;
		if (SUCCEEDED(hr))
		{
			ID2D1GeometrySink *pSink = NULL;

			hr = g_pSunGeometry->Open(&pSink);
			if (SUCCEEDED(hr))
			{
				pSink->SetFillMode(D2D1_FILL_MODE_WINDING);

				pSink->BeginFigure(
					D2D1::Point2F(270, 255),
					D2D1_FIGURE_BEGIN_FILLED
					);
				pSink->AddArc(
					D2D1::ArcSegment(
					D2D1::Point2F(440, 255), // end point
					D2D1::SizeF(85, 85),
					0.0f, // rotation angle
					D2D1_SWEEP_DIRECTION_CLOCKWISE,
					D2D1_ARC_SIZE_SMALL
					));            
				pSink->EndFigure(D2D1_FIGURE_END_CLOSED);

				pSink->BeginFigure(
					D2D1::Point2F(299, 182),
					D2D1_FIGURE_BEGIN_HOLLOW
					);
				pSink->AddBezier(
					D2D1::BezierSegment(
					D2D1::Point2F(299, 182),
					D2D1::Point2F(294, 176),
					D2D1::Point2F(285, 178)
					));
				pSink->AddBezier(
					D2D1::BezierSegment(
					D2D1::Point2F(276, 179),
					D2D1::Point2F(272, 173),
					D2D1::Point2F(272, 173)
					));
				pSink->EndFigure(D2D1_FIGURE_END_OPEN);

				pSink->BeginFigure(
					D2D1::Point2F(354, 156),
					D2D1_FIGURE_BEGIN_HOLLOW
					);
				pSink->AddBezier(
					D2D1::BezierSegment(
					D2D1::Point2F(354, 156),
					D2D1::Point2F(358, 149),
					D2D1::Point2F(354, 142)
					));
				pSink->AddBezier(
					D2D1::BezierSegment(
					D2D1::Point2F(349, 134),
					D2D1::Point2F(354, 127),
					D2D1::Point2F(354, 127)
					));
				pSink->EndFigure(D2D1_FIGURE_END_OPEN);

				pSink->BeginFigure(
					D2D1::Point2F(322,164),
					D2D1_FIGURE_BEGIN_HOLLOW
					);
				pSink->AddBezier(
					D2D1::BezierSegment(
					D2D1::Point2F(322, 164),
					D2D1::Point2F(322, 156),
					D2D1::Point2F(314, 152)
					));
				pSink->AddBezier(
					D2D1::BezierSegment(
					D2D1::Point2F(306, 149),
					D2D1::Point2F(305, 141),
					D2D1::Point2F(305, 141)
					));              
				pSink->EndFigure(D2D1_FIGURE_END_OPEN);

				pSink->BeginFigure(
					D2D1::Point2F(385, 164),
					D2D1_FIGURE_BEGIN_HOLLOW
					);
				pSink->AddBezier(
					D2D1::BezierSegment(
					D2D1::Point2F(385,164),
					D2D1::Point2F(392,161),
					D2D1::Point2F(394,152)
					));
				pSink->AddBezier(
					D2D1::BezierSegment(
					D2D1::Point2F(395,144),
					D2D1::Point2F(402,141),
					D2D1::Point2F(402,142)
					));                
				pSink->EndFigure(D2D1_FIGURE_END_OPEN);

				pSink->BeginFigure(
					D2D1::Point2F(408,182),
					D2D1_FIGURE_BEGIN_HOLLOW
					);
				pSink->AddBezier(
					D2D1::BezierSegment(
					D2D1::Point2F(408,182),
					D2D1::Point2F(416,184),
					D2D1::Point2F(422,178)
					));
				pSink->AddBezier(
					D2D1::BezierSegment(
					D2D1::Point2F(428,171),
					D2D1::Point2F(435,173),
					D2D1::Point2F(435,173)
					));
				pSink->EndFigure(D2D1_FIGURE_END_OPEN);
			}
			hr = pSink->Close();

			SAFE_RELEASE(pSink);
		}

		// Create river geometry
		hr = g_pD2DFactory->CreatePathGeometry(&g_pRiverGeometry) ;
		if (SUCCEEDED(hr))
		{
			ID2D1GeometrySink *pSink = NULL;

			hr = g_pRiverGeometry->Open(&pSink);
			if (SUCCEEDED(hr))
			{
				pSink->SetFillMode(D2D1_FILL_MODE_WINDING);
				pSink->BeginFigure(
					D2D1::Point2F(183, 392),
					D2D1_FIGURE_BEGIN_FILLED
					);
				pSink->AddBezier(
					D2D1::BezierSegment(
					D2D1::Point2F(238, 284),
					D2D1::Point2F(472, 345),
					D2D1::Point2F(356, 303)
					));
				pSink->AddBezier(
					D2D1::BezierSegment(
					D2D1::Point2F(237, 261),
					D2D1::Point2F(333, 256),
					D2D1::Point2F(333, 256)
					));
				pSink->AddBezier(
					D2D1::BezierSegment(
					D2D1::Point2F(335, 257),
					D2D1::Point2F(241, 261),
					D2D1::Point2F(411, 306)
					));
				pSink->AddBezier(
					D2D1::BezierSegment(
					D2D1::Point2F(574, 350),
					D2D1::Point2F(288, 324),
					D2D1::Point2F(296, 392)
					));
				pSink->EndFigure(D2D1_FIGURE_END_OPEN);
			}
			pSink->Close() ;
			SAFE_RELEASE(pSink) ;
		}
	}
}
Beispiel #11
0
HRESULT DemoApp::CreateDeviceIndependentResources()
{



	static const WCHAR msc_fontName[] = L"Verdana";   //사용할 폰트 이름
    static const FLOAT msc_fontSize = 20;			  //폰트 크기
	

    HRESULT hr = S_OK;
    ID2D1GeometrySink *pSink = NULL;

    // Create a Direct2D factory.
    hr = D2D1CreateFactory(D2D1_FACTORY_TYPE_SINGLE_THREADED, &m_pD2DFactory);
	
	if (SUCCEEDED(hr))
    {
        // Create WIC factory.
        hr = CoCreateInstance(CLSID_WICImagingFactory, NULL, CLSCTX_INPROC_SERVER, IID_PPV_ARGS(&m_pWICFactory));
    }

	if (SUCCEEDED(hr))
	{
        // Create a DirectWrite factory.
        hr = DWriteCreateFactory(
            DWRITE_FACTORY_TYPE_SHARED,
            __uuidof(m_pDWriteFactory),
            reinterpret_cast<IUnknown **>(&m_pDWriteFactory)
            );
    }
	 if (SUCCEEDED(hr))
    {
        // Create a DirectWrite text format object.
        hr = m_pDWriteFactory->CreateTextFormat(
            msc_fontName,
            NULL,
            DWRITE_FONT_WEIGHT_NORMAL,
            DWRITE_FONT_STYLE_NORMAL,
            DWRITE_FONT_STRETCH_NORMAL,
            msc_fontSize,
            L"", //locale
            &m_pTextFormat
            );
    }

		if (SUCCEEDED(hr))  //  바퀴벌레 기하
			{
				hr = m_pD2DFactory->CreateEllipseGeometry(D2D1::Ellipse(D2D1::Point2F(0,0), 10, 5),&m_pWheel);

			}

	
		if (SUCCEEDED(hr))  //  칼날 반원 기하
		{
			hr = m_pD2DFactory->CreatePathGeometry(&m_pPathGeometry);

			if (SUCCEEDED(hr))
			{
				// Write to the path geometry using the geometry sink.
				hr = m_pPathGeometry->Open(&pSink);

				if (SUCCEEDED(hr))
				{
					pSink->BeginFigure(
						D2D1::Point2F(200 , 100),  // 200 ,100
						D2D1_FIGURE_BEGIN_FILLED
						);
         

					pSink->AddBezier(D2D1::BezierSegment( D2D1::Point2F(220, 300), D2D1::Point2F(380, -100) , D2D1::Point2F(400, 100) ) );   // 220, 300    380 -100     400 100
					
			

					pSink->EndFigure(D2D1_FIGURE_END_CLOSED);


					hr = pSink->Close();
				}

				   SafeRelease(&pSink);
			}
		}


			if (SUCCEEDED(hr))  //  바퀴 경로 기하
			{
			hr = m_pD2DFactory->CreatePathGeometry(&m_wheelPath);

			if (SUCCEEDED(hr))
			{
				// Write to the path geometry using the geometry sink.
				hr = m_wheelPath->Open(&pSink);

				if (SUCCEEDED(hr))
				{
					pSink->BeginFigure(D2D1::Point2F(200,0),D2D1_FIGURE_BEGIN_FILLED);
          
				pSink->AddBezier(D2D1::BezierSegment(
					D2D1::Point2F(250,-50),D2D1::Point2F(80,-80),D2D1::Point2F(0,-50)));
				pSink->AddBezier(D2D1::BezierSegment(
					D2D1::Point2F(-50,-10),D2D1::Point2F(-180,-80),D2D1::Point2F(-200,0)));
				pSink->AddBezier(D2D1::BezierSegment(
					D2D1::Point2F(-230,60),D2D1::Point2F(-80,70),D2D1::Point2F(0,50)));
				pSink->AddBezier(D2D1::BezierSegment(
					D2D1::Point2F(50,10),D2D1::Point2F(180,80),D2D1::Point2F(200,0)));
					
					
		
					pSink->EndFigure(D2D1_FIGURE_END_CLOSED);

					hr = pSink->Close();
				}

				   SafeRelease(&pSink);
			}
		}



		
			if (SUCCEEDED(hr))  // 파리 경로 기하
			{
				hr = m_pD2DFactory->CreatePathGeometry(&m_flyPath);

			if (SUCCEEDED(hr))
			{
				// Write to the path geometry using the geometry sink.
				hr = m_flyPath->Open(&pSink);

				if (SUCCEEDED(hr))
				{
					pSink->BeginFigure(D2D1::Point2F(200,0),D2D1_FIGURE_BEGIN_FILLED);
          
				pSink->AddBezier(D2D1::BezierSegment(
					D2D1::Point2F(250,-50),D2D1::Point2F(80,-80),D2D1::Point2F(-100,-50)));
				pSink->AddBezier(D2D1::BezierSegment(
					D2D1::Point2F(-50,-10),D2D1::Point2F(-180,-80),D2D1::Point2F(-100,0)));
				pSink->AddBezier(D2D1::BezierSegment(
					D2D1::Point2F(-230,60),D2D1::Point2F(-80,70),D2D1::Point2F(50,50)));
				pSink->AddBezier(D2D1::BezierSegment(
					D2D1::Point2F(50,10),D2D1::Point2F(180,80),D2D1::Point2F(300,60)));
					
					
		
					pSink->EndFigure(D2D1_FIGURE_END_CLOSED);

					hr = pSink->Close();
				}

				   SafeRelease(&pSink);
			}
		}

			
	if(SUCCEEDED(hr)) //파리 몸통 기하
    {
        hr = m_pD2DFactory->CreateEllipseGeometry(
			D2D1::Ellipse(D2D1::Point2F(0,0), 20, 10), &m_pFlyGeometry);
    }
	if(SUCCEEDED(hr)) //파리 오른쪽 눈알 기하
    {
        hr = m_pD2DFactory->CreateEllipseGeometry(
			D2D1::Ellipse(D2D1::Point2F(20,-5), 5, 5), &m_pRightEyeGeometry);
    }
	if(SUCCEEDED(hr)) //파리 왼쪽 눈알 기하
    {
        hr = m_pD2DFactory->CreateEllipseGeometry(
			D2D1::Ellipse(D2D1::Point2F(20,5), 5, 5), &m_pLeftEyeGeometry);
    }

	if(SUCCEEDED(hr)) //파리 날개 가운데 기하
    {
        hr = m_pD2DFactory->CreatePathGeometry(&m_pMiddleWingGeometry);
        if(SUCCEEDED(hr))
        {
            ID2D1GeometrySink *pSink = NULL;

            hr = m_pMiddleWingGeometry->Open(&pSink);
            if (SUCCEEDED(hr))
            {
                pSink->SetFillMode(D2D1_FILL_MODE_WINDING);

                pSink->BeginFigure(
                    D2D1::Point2F(10, -9),
                    D2D1_FIGURE_BEGIN_FILLED
                    );

				pSink->AddLine(D2D1::Point2F(10, -15));
				pSink->AddArc(D2D1::ArcSegment(D2D1::Point2F(-10,-15),D2D1::SizeF(10,5),0,
					D2D1_SWEEP_DIRECTION_COUNTER_CLOCKWISE,D2D1_ARC_SIZE_SMALL));
				pSink->AddLine(D2D1::Point2F(-10, -9));
				pSink->AddLine(D2D1::Point2F(-10, 9));
				pSink->AddLine(D2D1::Point2F(-10, 15));
				pSink->AddArc(D2D1::ArcSegment(D2D1::Point2F(10,15),D2D1::SizeF(10,5),0,
					D2D1_SWEEP_DIRECTION_COUNTER_CLOCKWISE,D2D1_ARC_SIZE_SMALL));

                pSink->EndFigure(D2D1_FIGURE_END_CLOSED);
            }
            hr = pSink->Close();

            SafeRelease(&pSink);
       }
    }
	if(SUCCEEDED(hr)) //파리 날개 위쪽 기하
    {
        hr = m_pD2DFactory->CreatePathGeometry(&m_pUpWingGeometry);
        if(SUCCEEDED(hr))
        {
            ID2D1GeometrySink *pSink = NULL;

            hr = m_pUpWingGeometry->Open(&pSink);
            if (SUCCEEDED(hr))
            {
                pSink->SetFillMode(D2D1_FILL_MODE_WINDING);

                pSink->BeginFigure(
                    D2D1::Point2F(10, -9),
                    D2D1_FIGURE_BEGIN_FILLED
                    );

				pSink->AddLine(D2D1::Point2F(10, -15));
				pSink->AddArc(D2D1::ArcSegment(D2D1::Point2F(-10,-15),D2D1::SizeF(10,5),45,
					D2D1_SWEEP_DIRECTION_COUNTER_CLOCKWISE,D2D1_ARC_SIZE_SMALL));
				pSink->AddLine(D2D1::Point2F(-10, -9));
				pSink->AddLine(D2D1::Point2F(-10, 9));
				pSink->AddLine(D2D1::Point2F(-10, 15));
				pSink->AddArc(D2D1::ArcSegment(D2D1::Point2F(10,15),D2D1::SizeF(10,5),-45,
					D2D1_SWEEP_DIRECTION_COUNTER_CLOCKWISE,D2D1_ARC_SIZE_SMALL));

                pSink->EndFigure(D2D1_FIGURE_END_CLOSED);
            }
            hr = pSink->Close();

            SafeRelease(&pSink);
       }
    }
	if(SUCCEEDED(hr)) //파리 날개 아래쪽 기하
    {
        hr = m_pD2DFactory->CreatePathGeometry(&m_pDownWingGeometry);
        if(SUCCEEDED(hr))
        {
            ID2D1GeometrySink *pSink = NULL;

            hr = m_pDownWingGeometry->Open(&pSink);
            if (SUCCEEDED(hr))
            {
                pSink->SetFillMode(D2D1_FILL_MODE_WINDING);

                pSink->BeginFigure(
                    D2D1::Point2F(10, -9),
                    D2D1_FIGURE_BEGIN_FILLED
                    );

				pSink->AddLine(D2D1::Point2F(10, -15));
				pSink->AddArc(D2D1::ArcSegment(D2D1::Point2F(-10,-15),D2D1::SizeF(10,5),-45,
					D2D1_SWEEP_DIRECTION_COUNTER_CLOCKWISE,D2D1_ARC_SIZE_SMALL));
				pSink->AddLine(D2D1::Point2F(-10, -9));
				pSink->AddLine(D2D1::Point2F(-10, 9));
				pSink->AddLine(D2D1::Point2F(-10, 15));
				pSink->AddArc(D2D1::ArcSegment(D2D1::Point2F(10,15),D2D1::SizeF(10,5),45,
					D2D1_SWEEP_DIRECTION_COUNTER_CLOCKWISE,D2D1_ARC_SIZE_SMALL));

                pSink->EndFigure(D2D1_FIGURE_END_CLOSED);
            }
            hr = pSink->Close();

            SafeRelease(&pSink);
       }
    }


	m_pWingGeometry[0] = m_pMiddleWingGeometry;	//중간위치의 날개
	m_pWingGeometry[1] = m_pUpWingGeometry;		//위쪽 위치의 날개
	m_pWingGeometry[2] = m_pMiddleWingGeometry;	//중간위치의 날개
	m_pWingGeometry[3] = m_pDownWingGeometry;	//아래쪽 위치의 날개

    return hr;
}
Beispiel #12
0
int _tmain(int argc, _TCHAR* argv[])
{
    HRESULT hr = S_OK;

    // Create a Direct2D factory.
    CHECKHR(D2D1CreateFactory(D2D1_FACTORY_TYPE_SINGLE_THREADED, &g_pD2DFactory));

    // Create a DirectWrite factory.
    CHECKHR(DWriteCreateFactory(DWRITE_FACTORY_TYPE_SHARED, __uuidof(IDWriteFactory),
        reinterpret_cast<IUnknown**>(&g_pDWriteFactory)));

    // Create a WIC factory
    IWICImagingFactory* pWICFactory = NULL;

    CHECKHR(CoInitialize(nullptr));
    CHECKHR(CoCreateInstance(CLSID_WICImagingFactory1, nullptr, CLSCTX_INPROC_SERVER,
        IID_IWICImagingFactory, (LPVOID*)&pWICFactory));

    // Create an IWICBitmap and RT
    IWICBitmap* pWICBitmap = NULL;
    static const UINT sc_bitmapWidth = 640;
    static const UINT sc_bitmapHeight = 480;

    CHECKHR(pWICFactory->CreateBitmap(sc_bitmapWidth, sc_bitmapHeight, GUID_WICPixelFormat32bppBGR,
        WICBitmapCacheOnLoad,
        &pWICBitmap));

    // Set the render target type to D2D1_RENDER_TARGET_TYPE_DEFAULT to use software rendering.
    CHECKHR(g_pD2DFactory->CreateWicBitmapRenderTarget(
        pWICBitmap, D2D1::RenderTargetProperties(), &g_pRenderTarget));

    // Create text format and a path geometry representing an hour glass. 
    IDWriteTextFormat*  pTextFormat = NULL;
    static const WCHAR sc_fontName[] = L"Calibri";
    static const FLOAT sc_fontSize = 50;

    CHECKHR(g_pDWriteFactory->CreateTextFormat(
        sc_fontName,
        NULL,
        DWRITE_FONT_WEIGHT_NORMAL,
        DWRITE_FONT_STYLE_NORMAL,
        DWRITE_FONT_STRETCH_NORMAL,
        sc_fontSize,
        L"", //locale
        &pTextFormat
        ));

    CHECKHR(pTextFormat->SetTextAlignment(DWRITE_TEXT_ALIGNMENT_CENTER));
    CHECKHR(pTextFormat->SetParagraphAlignment(DWRITE_PARAGRAPH_ALIGNMENT_CENTER));

    // Create a path geometry
    ID2D1PathGeometry* pPathGeometry = NULL;
    ID2D1GeometrySink* pSink = NULL;

    CHECKHR(g_pD2DFactory->CreatePathGeometry(&pPathGeometry));
    CHECKHR(pPathGeometry->Open(&pSink));

    pSink->SetFillMode(D2D1_FILL_MODE_ALTERNATE);

    pSink->BeginFigure(
        D2D1::Point2F(0, 0),
        D2D1_FIGURE_BEGIN_FILLED
        );

    pSink->AddLine(D2D1::Point2F(200, 0));

    pSink->AddBezier(
        D2D1::BezierSegment(
        D2D1::Point2F(150, 50),
        D2D1::Point2F(150, 150),
        D2D1::Point2F(200, 200))
        );

    pSink->AddLine(D2D1::Point2F(0, 200));

    pSink->AddBezier(
        D2D1::BezierSegment(
        D2D1::Point2F(50, 150),
        D2D1::Point2F(50, 50),
        D2D1::Point2F(0, 0))
        );

    pSink->EndFigure(D2D1_FIGURE_END_CLOSED);

    CHECKHR(pSink->Close());

    // Create GradientStopCollection
    ID2D1GradientStopCollection *pGradientStops = NULL;
    static const D2D1_GRADIENT_STOP stops[] =
    {
        { 0.f, { 0.f, 1.f, 1.f, 1.f } },
        { 1.f, { 0.f, 0.f, 1.f, 1.f } },
    };

    CHECKHR(g_pRenderTarget->CreateGradientStopCollection(
        stops,
        ARRAYSIZE(stops),
        &pGradientStops
        ));

    ID2D1LinearGradientBrush* pLGBrush = NULL;
    ID2D1SolidColorBrush* pBlackBrush = NULL;

    CHECKHR(g_pRenderTarget->CreateLinearGradientBrush(
        D2D1::LinearGradientBrushProperties(
        D2D1::Point2F(100, 0),
        D2D1::Point2F(100, 200)),
        D2D1::BrushProperties(),
        pGradientStops,
        &pLGBrush
        ));

    CHECKHR(g_pRenderTarget->CreateSolidColorBrush(
        D2D1::ColorF(D2D1::ColorF::Black),
        &pBlackBrush
        ));

    // Render into the bitmap.
    g_pRenderTarget->BeginDraw();
    g_pRenderTarget->Clear(D2D1::ColorF(D2D1::ColorF::White));
    D2D1_SIZE_F rtSize = g_pRenderTarget->GetSize();

    // Set the world transform to a 45 degree rotation at the center of the render target
    // and write "Hello, World".
    g_pRenderTarget->SetTransform(
        D2D1::Matrix3x2F::Rotation(
        45,
        D2D1::Point2F(
        rtSize.width / 2,
        rtSize.height / 2))
        );

    static const WCHAR sc_helloWorld[] = L"Hello, World!";
    g_pRenderTarget->DrawText(
        sc_helloWorld,
        ARRAYSIZE(sc_helloWorld) - 1,
        pTextFormat,
        D2D1::RectF(0, 0, rtSize.width, rtSize.height),
        pBlackBrush);

    // Reset back to the identity transform.
    g_pRenderTarget->SetTransform(D2D1::Matrix3x2F::Translation(0, rtSize.height - 200));
    g_pRenderTarget->FillGeometry(pPathGeometry, pLGBrush);
    g_pRenderTarget->SetTransform(D2D1::Matrix3x2F::Translation(rtSize.width - 200, 0));
    g_pRenderTarget->FillGeometry(pPathGeometry, pLGBrush);
    CHECKHR(g_pRenderTarget->EndDraw());

    // Save the image to a file.
    IWICStream* pStream = NULL;
    CHECKHR(pWICFactory->CreateStream(&pStream));

    // Use InitializeFromFilename to write to a file. If there is need to write inside the memory, use InitializeFromMemory. 
    static const WCHAR filename[] = L"output.png";
    CHECKHR(pStream->InitializeFromFilename(filename, GENERIC_WRITE));

    IWICBitmapEncoder* pEncoder = NULL;
    CHECKHR(pWICFactory->CreateEncoder(GUID_ContainerFormatPng, NULL, &pEncoder));
    CHECKHR(pEncoder->Initialize(pStream, WICBitmapEncoderNoCache));

    IWICBitmapFrameEncode* pFrameEncode = NULL;
    CHECKHR(pEncoder->CreateNewFrame(&pFrameEncode, NULL));

    // Use IWICBitmapFrameEncode to encode the bitmap into the picture format you want.
    CHECKHR(pFrameEncode->Initialize(NULL));
    CHECKHR(pFrameEncode->SetSize(sc_bitmapWidth, sc_bitmapHeight));

    WICPixelFormatGUID format = GUID_WICPixelFormatDontCare;
    CHECKHR(pFrameEncode->SetPixelFormat(&format));
    CHECKHR(pFrameEncode->WriteSource(pWICBitmap, NULL));
    CHECKHR(pFrameEncode->Commit());
    CHECKHR(pEncoder->Commit());

    return 0;
}
HRESULT DemoApp::CreateGeometries()
{
    HRESULT hr = S_OK;

    if (!m_pGeometry)
    {
        IGeometryRealizationFactory *pRealizationFactory = NULL;
        IGeometryRealization *pRealization = NULL;

        ID2D1TransformedGeometry *pGeometry = NULL;
        ID2D1PathGeometry *pPathGeometry = NULL;
        ID2D1GeometrySink *pSink = NULL;

        float squareWidth = 0.9f * sc_boardWidth / m_numSquares;

        // Create the path geometry.
        hr = m_pD2DFactory->CreatePathGeometry(&pPathGeometry);
        if (SUCCEEDED(hr))
        {
            // Write to the path geometry using the geometry sink to 
            // create an hour glass shape.
            hr = pPathGeometry->Open(&pSink);
        }
        if (SUCCEEDED(hr))
        {
            pSink->SetFillMode(D2D1_FILL_MODE_ALTERNATE);

            pSink->BeginFigure(
                D2D1::Point2F(0, 0),
                D2D1_FIGURE_BEGIN_FILLED
                );

            pSink->AddLine(D2D1::Point2F(1.0f, 0));

            pSink->AddBezier(
                D2D1::BezierSegment(
                    D2D1::Point2F(0.75f, 0.25f),
                    D2D1::Point2F(0.75f, 0.75f),
                    D2D1::Point2F(1.0f, 1.0f))
                );

            pSink->AddLine(D2D1::Point2F(0, 1.0f));

            pSink->AddBezier(
                D2D1::BezierSegment(
                    D2D1::Point2F(0.25f, 0.75f),
                    D2D1::Point2F(0.25f, 0.25f),
                    D2D1::Point2F(0, 0))
                );

            pSink->EndFigure(D2D1_FIGURE_END_CLOSED);

            hr = pSink->Close();
        }

        if (SUCCEEDED(hr))
        {
            D2D1_MATRIX_3X2_F scale = D2D1::Matrix3x2F::Scale(squareWidth, squareWidth);
            D2D1_MATRIX_3X2_F translation = D2D1::Matrix3x2F::Translation(-squareWidth / 2, -squareWidth / 2);

            hr = m_pD2DFactory->CreateTransformedGeometry(
                    pPathGeometry,
                    scale * translation,
                    &pGeometry
                    );
        }

        if (SUCCEEDED(hr))
        {
            // Transfer the reference.
            m_pGeometry = pGeometry;
            pGeometry = NULL;
        }

        SafeRelease(&pRealizationFactory);
        SafeRelease(&pRealization);
        SafeRelease(&pGeometry);
        SafeRelease(&pPathGeometry);
        SafeRelease(&pSink);
    }

    return hr;
}