DirectXTKで簡単に3D空間上に基本の三角形ポリゴンを描画してみた

こんにちは!有栖(すー)です!最近、就活が本格化してきて頑張らなきゃな。。ってなってます。いい会社に巡り合えるといいなぁ。。

目次

・どうしてこの記事(DirectXTKの記事)を書こうとしたの?
・本題
 ・前提
 ・三角形ポリゴンを出すイメージ
 ・三角形ポリゴンを描画するのに必要なもの
 ・実際のコード
 ・細かい補足

どうしてこの記事を書こうと思ったのか

本題に入る前に今回どうしてこんな記事を書こうと思ったのかということなんだけども。。
実は私の学校の方針でDirectX9は古いバージョンだし11や12は難しいからとりあえず11の開発環境に近いけど少し簡単にできるTKを使ってみようということになりました。
そこでゲーム開発を進めていくんですけど参考資料がとってもすくなくてDirectX11のものを翻訳してTK版に直してってことをしてたんです。
ちょっとめんどくさいじゃないですかw
だったら自分で記事書こうかなぁと思い書いてみます。
暖かく見守ってください(*'ω'*)

それでは本題に入っていきます!

本題

前提

まず前提としてDirectXTKを基本設定を終えているということを前提にさせてもらいます。
こちらにセットアップの方法が詳しく書いてあった記事があったのでできていない方は先にやってもらえるとうれしいです。

また今回はHLSLを書かずに比較的簡単にできる方法で行います。

三角形ポリゴンを出すイメージ

簡単に図解すると。。

イメージこんな感じ
初めはイメージこんな感じかな見たいな感じで大丈夫だと思う(そうだと思いたい)

難しく言うと。。
カメラを設定してカメラの描画範囲を決め、そこからさらに三角形を置き、なんやかんやの設定してーーーーみたいな感じなんだけど難しいのでカットします!!(気が向いたらそのうち書きます)

三角形ポリゴンを出すために必要なもの

・三角形の頂点情報
・ベーシックエフェクト(DirectX::BasicEffect)
 実は内部的にシェーダー使ってるのでその設定に使うもの
・プリミティブバッチ(DirectX::PrimitiveBatch)
 線や三角形等の動的に生成されたジオメトリを簡単に描画できるクラス
・ポリゴンに色を付けるか決める。
 今回は色付けようと思います。
・コモンステータス(DirectX::CommonStates)
 Direct3Dレンダリング状態の一般的な組み合わせの設定を簡素化するファ
 クトリ
・デバイスリソーシーズ(DX::DeviceResources)
 デバイスとスワップチェーンの抽象化で、オプションで深度バッファー
 シングルトン化しとくと超便利

って書かれてもしっくりこないと思うのでコードに行っちゃいます

実際のコード

#pragma once
// 三角形の描画クラス
class Triangle
{
public:
    Triangle(DX::DeviceResources* deviceResources,int height,int width);
    ~Triangle()=defult;
    void Draw();
private:
    // ベーシックエフェクト
    std::unique_ptr DirectX::BasicEffect mBasicEffect;
    // プリミティブバッチ  プリミティブバッチの<>の中はどのような描画タイプか決めています。
    std::unique_ptr <DirectX::PrimitiveBatch DirectX::VertexPositionColor> mPritiveBatch;
    // コモンステータス
    std::unique_ptr DirectX::CommonStates mStates;
    // インプットレイアウト
    Microsoft::WRL::ComPtr <ID3D11InputLayout> mInputLayout;
    // デバイスリソーシーズ
    DX::DeviceResources* mDeviceResources;
};

Triangle.h

#include "pch.h"
#include "triangle.h"
Triangle::Triangle(DX::DeviceResources* deviceResources, int hight, int width)
{
     //  デバイスリソーシーズの取得
     mDeviceResources = deviceResources;
     auto device = deviceResources->GetD3DDevice();
     auto devicrContext = deviceResources->GetD3DDeviceContext();

     //  ベーシックエフェクトの初期化、プロジェクション行列の生成しセット
     /*
	XMMatrixOrthographicOffCenterRH 引数は
	見える範囲の X の最小値,見える範囲の X の最大値
	見える範囲の Y の最小値,見える範囲の Y の最大値
	一番近い描画平面までの距離,一番遠い描画平面までの距離
     */  
     mBasicEffect = std::make_unique<DirectX::BasicEffect>(device);
     ->SetProjection(DirectX::XMMatrixOrthographicOffCenterRH(
	0, width, 0, hight, 0.1f, 100
     ));

     // 今回はカラーテクスチャの方にしたので true にします。
     mBasicEffect->SetVertexColorEnabled(true);

     // コモンステータスの作成
     mStates = std::make_unique<DirectX::CommonStates>(device);

     // シェーダーデータの生成と取得
     void  const* shaderByteCode;
     size_t byteCodeLength;
     mBasicEffect->GetVertexShaderBytecode(&shaderByteCode,&byteCodeLength);

     // インプットレイアウトの生成
     device->CreateInputLayout(
        DirectX::VertexPositionColor::InputElements,
	DirectX::VertexPositionColor::InputElementCount,
	shaderByteCode,
	byteCodeLength,
	mInputLayout.ReleaseAndGetAddressOf());
     mPritiveBatch = std::make_unique<DirectX::PrimitiveBatch<DirectX::VertexPositionColor>>(devicrContext);

     // ステートの設定
     devicrContext->OMSetBlendState(mStates->Opaque(), nullptr, 0xFFFFFFFF);
     devicrContext->OMSetDepthStencilState(mStates->DepthNone(), 0);
     devicrContext->RSSetState(mStates->CullNone());
     devicrContext->IASetInputLayout(mInputLayout.Get());

     // 視点とターゲットとカメラの向きを設定
     DirectX::SimpleMath::Matrix view, projection;
     DirectX::SimpleMath::Vector3    eye(0.0f, 0.0f, 10.0f);
     DirectX::SimpleMath::Vector3 target(0.0f, 0.0f, 0.0f);
     DirectX::SimpleMath::Vector3     up(0.0f, 1.0f, 0.0f);

     //エフェクトに各種変換行列の設定ー>設定がまずいと見た目が正しくならない
     view = DirectX::SimpleMath::Matrix::CreateLookAt(eye, target, up);

     // 画角、仮面の縦横比(アスペクト比)、一番近い投影面、一番遠い投影面 の設定
     constexpr float fieldOfView = DirectX::XMConvertToRadians(45.0f);    // 画角
     float aspectRatio = (float)width / (float)hight;	         // 画面縦横比
     float nearPlane = 0.1f;                           //一番近い投影面
     float farPlane = 100.0f;                                             // 一番遠い投影面

     //プロジェクション行列の生成
     projection = DirectX::SimpleMath::Matrix::CreatePerspectiveFieldOfView(fieldOfView, aspectRatio, nearPlane, farPlane);

     //ビュー行列の設定
     mBasicEffect->SetView(view);	
     //射影行列の設定		
     mBasicEffect->SetProjection(projection);
}

void Triangle::Draw(){
     // デバイスコンテキストの取得
     auto devicrContext = mDeviceResources->GetD3DDeviceContext();//ワールド座標の生成(今回は動かさないので Identity のままで行きます。
    
   // ワールド座標の生成
     DirectX::SimpleMath::Matrix world=DirectX::SimpleMath::Matrix::Identity;
     
     // ここでワールド座標をいじるならここ ↓ 
     // コメントアウトしてある処理は毎フレームY軸方向に1度ずつ回転させている
     //static int rad = 0;
     //rad++;
     //world = DirectX::SimpleMath::Matrix::CreateRotationY(DirectX::XMConvertToRadians(rad));

     // ワールド座標の設定
     mBasicEffect->SetWorld(world);

     // ベーシックエフェクトの変更の適用
     mBasicEffect->Apply(devicrContext);


     // ここは関数化してもいいかも
     // 三角形の形の設定 今回は形を変えるつもりはないのでベタ打ちしてるけど Vector3 のところの数値を変えると変形できる。
     static const DirectX::VertexPositionColor vertices[3] =
     {
	DirectX::VertexPositionColor(DirectX::SimpleMath::Vector3(0.0f,1.0f,0.0f),DirectX::Colors::Red),
	DirectX::VertexPositionColor(DirectX::SimpleMath::Vector3(1.0f,0.0f,0.0f),DirectX::Colors::Green),
	DirectX::VertexPositionColor(DirectX::SimpleMath::Vector3(-1.0f,0.0f,0.0f),DirectX::Colors::Blue),
     };
     //プリミティブの描画
     mPritiveBatch->Begin();
     mPritiveBatch->DrawTriangle(vertices[0], vertices[1], vertices[2]);
     mPritiveBatch->End();
}

Triangle.cpp

実行結果が下になります(*'ω'*)

三角形をだすプログラムの実行結果

超長くなっちゃったけどこんな感じでした~~!
三角形をだすだけでこんなにコード書くのか(白目)ってなっちゃいますよねぇ。。。
こう思うとゲームエンジンってすごいなぁと思う今日この頃でした(*'ω'*)

次はいろんな形のポリゴンを作ってみようと思います。

間違い等があったらご指摘お願いいたします。
それではまた(*'ω'*)


この記事が気に入ったらサポートをしてみませんか?