9
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 3 years have passed since last update.

Siv3DAdvent Calendar 2021

Day 5

[OpenSiv3D]DrawTrianglesใ‚’ไฝฟใฃใฆ๐ŸŸใ‚’ใ„ใฃใฑใ„ๆณณใŒใใ†

Posted at

ใฏใ˜ใ‚ใซ

ๆฐดๆ—้คจใ„ใใŸใใชใ„ใงใ™ใ‹๏ผŸ๏ผŸ
ๅƒ•ใฏๆฐดๆ—้คจใŒๅฅฝใใชใฎใงๅฎšๆœŸ็š„ใซ่กŒใใŸใ„ๆฐ—ๆŒใกใซใชใ‚Šใพใ™ใ€‚
(ไธ€็ท’ใซ่กŒใไบบใŒใ„ใชใ„ใฎใงใ€ใผใฃใกใงใฏ่กŒใใพใ›ใ‚“)

ใใ—ใฆใตใจๆ€ใ„ใพใ—ใŸใ€‚

ใ›ใ‚„ใ€
$\huge{๐ŸŸ๐ŸŸ๐ŸŸใŠ้ญšใ•ใ‚“ใ‚’100ไธ‡ไฝ“ๆณณใŒใใ†๐ŸŸ๐ŸŸ๐ŸŸ}$

ๅฎ‰ๆ˜“ใชๅฎŸ่ฃ…

Main.cpp
# include <Siv3D.hpp>

void Main()
{
	// ๐ŸŸใŠ้ญšใ•ใ‚“ใ‚’ๆณณใŒใ™ใž๏ฝž๏ฝž๐ŸŸ
	Texture tex(Emoji(U"๐ŸŸ"));
	auto scaledTex = tex.scaled(0.3);
	const auto& texSize = scaledTex.size;

	// ๐ŸŸ 100ไธ‡ไฝ“ๆณณใŒใ™ใž๏ฝž๐ŸŸ
	constexpr size_t fishCount = 1000000;
	constexpr double sqrtFishCount = 1000.0;

	// ๐ŸŸ ้ฉๅฝ“ใซๅบงๆจ™่จˆ็ฎ—๐ŸŸ
	Array<Vec2> positions;
	positions.reserve(fishCount);
	for (size_t count = 0; count < fishCount; ++count) {
		positions << static_cast<Vec2>(texSize) * Vec2{
			Math::Fmod(count, sqrtFishCount),
			count / sqrtFishCount
		};
	}

	while (System::Update())
	{
		ClearPrint();
		Print << texSize;
		Print << Profiler::FPS();

		// ๐ŸŸ ใŠ้ญšใ•ใ‚“ๆ็”ป๏ผ๏ผ๐ŸŸ
		for (const auto& pos : positions) {
			scaledTex.drawAt(pos);
		}
	}
}

ใŠๆฐ—ใฅใใงใ—ใ‚‡ใ†ใ‹๏ผŸ
FPSใŒ10ใพใง่ฝใกใฆใ€็„กไบ‹ๆญปไบกใ—ใพใ—ใŸใ€‚
(ใชใŠใ€ใƒชใƒชใƒผใ‚นใƒ“ใƒซใƒ‰ใงใ‚‚ๅŒๆง˜ใงใ™ใ€‚)


โ€ปๅฎŸ้š›ใซใฏใ€ใ“ใฎใ‚„ใ‚Šๆ–นใ ใจใ—ใฆใ‚‚็”ป้ขๅค–ใฎใŠ้ญšใ•ใ‚“ใฏๆ็”ปใ—ใชใ„ใ‚ˆใ†ใซใ™ใ‚‹ใชใฉใฎๅฏพๅฟœใ‚’ใ—ใŸใปใ†ใŒใ‚ˆใ„ใจๆ€ใ„ใพใ™๐ŸŸ

		auto screenRect = Scene::Rect();
		for (const auto& pos : positions) {
			if (!screenRect.intersects(scaledTex.regionAt(pos))) {
				// ็”ป้ขๅค–ใฎใ‚‚ใฎใฏ็„ก่ฆ–
				continue;
			}
			scaledTex.drawAt(pos);
		}

ใงใฏใฉใ†ใ™ใ‚Œใฐใ€ใŠ้ญšใ•ใ‚“ใ‚’100ไธ‡ไฝ“ๆณณใŒใ™ใ“ใจใŒใงใใ‚‹ใฎใ‹

DrawTriangles

ใƒœใƒˆใƒซใƒใƒƒใ‚ฏใฏใฉใ“ใŒใ‚ใ‚Šใใ†ใงใ—ใ‚‡ใ†ใ‹โ€ฆ
ใใ‚‚ใใ‚‚100ไธ‡ใƒซใƒผใƒ—ใ‚‚่ปฝใใฏใชใ„ใจๆ€ใ„ใพใ™ใŒ
100ไธ‡ๅ›žๆ็”ปๅ‘ฝไปคใ‚’ใ—ใฆใ„ใ‚‹ใฎใฏใจใฆใ‚‚้‡ใใ†ใงใ™ใ€‚
(1ๅ€‹็”ปๅƒใ‚’็”ป้ขใซๅ‡บใ™ใ ใ‘ใงใ‚‚่ฃใงใฏใ„ใ‚ใ„ใ‚ใชๅ‡ฆ็†ใ‚’ใ‚„ใฃใฆใ„ใ‚‹ใฎใงใ™ใ€‚)

ใ“ใฎๆ‚ฉใฟใ‚’่งฃๆฑบใ—ใฆใใ‚Œใ‚‹ใฎใŒใ€ไปŠๅ›žใ”็ดนไป‹ใ™ใ‚‹ใƒกใ‚ฝใƒƒใƒ‰
๐ŸŸ**s3d::Graphics2D::DrawTriangles(uint32 count)**๐ŸŸ
ใงใ™ใ€‚

ใ“ใฎ้–ขๆ•ฐใฏใ€
ๅผ•ๆ•ฐใงๆธกใ—ใŸๆ•ฐใ ใ‘ไธ‰่ง’ๅฝขใ‚’ๆ็”ปใ™ใ‚‹้–ขๆ•ฐใงใ™ใ€‚
ใจใ€่จ€ใ„ใพใ—ใŸใŒๅฎŸ้š›ใซใ“ใฎใƒกใ‚ฝใƒƒใƒ‰ใ‚’ๅ‘ผใ‚“ใงใ‚‚ไธ‰่ง’ๅฝขโ–ณใฏๆ็”ปใ•ใ‚Œใชใ„ใงใ—ใ‚‡ใ†ใ€‚
ไธ‰่ง’ๅฝขใฎๅบงๆจ™ใ‚„ใ€่‰ฒใชใฉใฎ้ ‚็‚นๆƒ…ๅ ฑใ‚’ไฝ•ไธ€ใค่จญๅฎšใ—ใฆใ„ใชใ„ใ‹ใ‚‰ใงใ™ใ€‚

ใงใฏใ€ใใ†ใ„ใฃใŸ้ ‚็‚นๆƒ…ๅ ฑใ‚’ใฉใ†ใ‚„ใฃใฆ่จญๅฎšใ™ใ‚‹ใฎใ‹ใจใ„ใ†ใจใ€้ ‚็‚นใ‚ทใ‚งใƒผใƒ€ใƒผใ‚’ไฝฟใ„ใพใ™ใ€‚

(ไฝ™่ซ‡ใงใ™ใŒใ€ๆ—งSiv3Dใซใ‚‚้กžไผผใฎ้–ขๆ•ฐใŒใ‚ใ‚Šใพใ—ใŸใŒใ€ใ“ใฎๆ™‚ใฏไธ‰่ง’ๅฝขใฎๆ•ฐใงใฏใชใ้ ‚็‚นๆ•ฐใ‚’ๆธกใ™ใƒกใ‚ฝใƒƒใƒ‰ใ ใฃใŸใฎใงใ€ๅฐ‘ใ—ใ ใ‘ไฝฟใ„ๆ–นใŒๅค‰ใ‚ใฃใฆใ„ใพใ™ใ€‚)

Main.cpp
# include <Siv3D.hpp>

void Main()
{
	// ๐ŸŸใŠ้ญšใ•ใ‚“ใ‚’ๆณณใŒใ™ใž๏ฝž๏ฝž๐ŸŸ
	Texture tex(Emoji(U"๐ŸŸ"));

	// ๐ŸŸ 100ไธ‡ไฝ“ๆณณใŒใ™ใž๏ฝž๐ŸŸ
	constexpr size_t fishCount = 1000000;

	// ใ‚ทใ‚งใƒผใƒ€ใƒผ
	const FilePath shaderPath{ U"osakana_san.hlsl" };
	VertexShader vs = HLSL{ shaderPath };
	PixelShader ps = HLSL{ shaderPath };

	while (System::Update())
	{
		ClearPrint();
		Print << Profiler::FPS();

		// ๐ŸŸ ใŠ้ญšใ•ใ‚“ๆ็”ป๏ผ๏ผ๐ŸŸ
		{
			// ใ‚ทใ‚งใƒผใƒ€ใƒผ่จญๅฎš
			ScopedCustomShader2D scopedShder{ vs, ps };

			// PSใงไฝฟใ†ใ‚ˆใ†ใซใƒ†ใ‚ฏใ‚นใƒใƒฃใ‚’ใ‚ปใƒƒใƒˆ
			s3d::Graphics2D::SetPSTexture(0, tex);

			// 100ไธ‡ * 2ๅ€‹ใฎไธ‰่ง’ๅฝขๆ็”ป
			// ๅ››่ง’ๅฝขใฎๆ็”ปใซใฏไธ‰่ง’ๅฝขใŒ2ใคใ„ใ‚‹ใฎใง2ๅ€ใซใ—ใฆใ‚‹
			s3d::Graphics2D::DrawTriangles(fishCount * 2);
		}
	}
}

ๅ››่ง’ๅฝขใฎ็”ปๅƒใ‚’ๆ็”ปใ™ใ‚‹ใŸใ‚ใซใฏไธ‰่ง’ๅฝขใŒ2ใคๅฟ…่ฆใชใฎใงใ€ๆ็”ปใ—ใŸใ„ๆ•ฐใซ2ๅ€ใ‚’ใ‹ใ‘ใ‚‹ๅฟ…่ฆใŒใ‚ใ‚Šใพใ™ใ€‚

ใŠ้ญšใ•ใ‚“ใฎใƒ†ใ‚ฏใ‚นใƒใƒฃใ‚’ๅผตใ‚Šไป˜ใ‘ใŸใ„ใฎใงใ€ใƒ”ใ‚ฏใ‚ปใƒซใ‚ทใ‚งใƒผใƒ€ใƒผใ‚‚ไฝฟใฃใฆใ„ใพใ™ใ€‚

โ€ปๆณจๆ„๏ผšใ“ใฎ่จ˜ไบ‹ใงใฏHLSLใงใ‚ทใ‚งใƒผใƒ€ใƒผใ‚’ๆ›ธใใพใ™ใŒใ€ใƒ—ใƒฉใƒƒใƒˆใƒ•ใ‚ฉใƒผใƒ ใซๅฟœใ˜ใฆใฏGLSLใ‚’ไฝฟ็”จใ™ใ‚‹ๅฟ…่ฆใŒใ‚ใ‚Šใพใ™ใ€‚

้ ‚็‚นใ‚ทใ‚งใƒผใƒ€ใƒผใง่จˆ็ฎ—

่จˆ็ฎ—ใ—ใพใ—ใŸใ€‚(ๅฎŒ)

osakana_san.hlsl
Texture2D		g_texture0 : register(t0);
SamplerState	g_sampler0 : register(s0);

namespace s3d
{
    //
    //	VS Input (nothing)
    //

    //
    //	VS Output
    //
    struct PSInput
    {
        float4 position	: SV_POSITION;
        float4 color	: COLOR0;
        float2 uv		: TEXCOORD0;
    };

    //
    //	Siv3D Functions
    //
    float4 Transform2D(float2 pos, float2x4 t)
    {
        return float4((t._13_14 + (pos.x * t._11_12) + (pos.y * t._21_22)), t._23_24);
    }
}

//
//	Constant Buffer
//
cbuffer VSConstants2D : register(b0)
{
    row_major float2x4 g_transform;
    float4 g_colorMul;
}

cbuffer PSConstants2D : register(b0)
{
    float4 g_colorAdd;
    float4 g_sdfParam;
    float4 g_sdfOutlineColor;
    float4 g_sdfShadowColor;
    float4 g_internal;
}

//-------------------------------------------
// ้ ‚็‚นใ‚ทใ‚งใƒผใƒ€ใƒผ

float2 toUV(uint mod6)
{
    if (mod6 == 0) {
        return float2(0, 0);
    } else if (mod6 == 1) {
        return float2(1, 0);
    } else if (mod6 == 2) {
        return float2(0, 1);
    } else if (mod6 == 3) {
        return float2(0, 1);
    } else if (mod6 == 4) {
        return float2(1, 0);
    } else {
        return float2(1, 1);
    }
}

float2 toQuad(float2 uv, float2 size)
{
    float2 halfSize = size / 2.0;
    float2 ret = lerp(-halfSize, halfSize, uv);
    return ret;
}

s3d::PSInput VS(uint id: SV_VERTEXID)
{
    s3d::PSInput result;
    // ไธ€ๅŒนใฎใŠ้ญšใ•ใ‚“ใซๅฟ…่ฆใช้ ‚็‚นใฏ 6 
    const uint quadId = id / 6;
    const uint mod6 = id % 6;

    // ๅบงๆจ™ใ‚’้ฉๅฝ“ใซ่จˆ็ฎ—
    float2 pos = float2(0, 0);
    const uint sqrtFishCount = 1000;
    const int xId = (int)(quadId % sqrtFishCount);
    const int yId = (int)(quadId / sqrtFishCount);

    float2 size = float2(40.8, 38.4);
    pos += float2(xId * size.x, yId * size.y);

    // uvๅบงๆจ™ใ‚’่จˆ็ฎ—
    float2 uv = toUV(mod6);
    // ๅ››่ง’ๅฝขใซใ™ใ‚‹
    pos += toQuad(uv, size);

    result.position = s3d::Transform2D(pos, g_transform);
    result.uv = uv;
    result.color = g_colorMul;

    return result;
}

//-------------------------------------------
// ใƒ”ใ‚ฏใ‚ปใƒซใ‚ทใ‚งใƒผใƒ€ใƒผ

float4 PS(s3d::PSInput input) : SV_TARGET
{
    const float4 texColor = g_texture0.Sample(g_sampler0, input.uv);
    return (texColor * input.color) + g_colorAdd;
}

โ€ฆ
ใ‚‚ใ†ๅฐ‘ใ—็ดฐใ‹ใ่ฆ‹ใฆใ„ใใพใ™ใ€‚

namespace s3d
{
    //
    //	VS Input (nothing)
    //

    //
    //	VS Output
    //
    struct PSInput
    {
        float4 position	: SV_POSITION;
        float4 color	: COLOR0;
        float2 uv		: TEXCOORD0;
    };

    //
    //	Siv3D Functions
    //
    float4 Transform2D(float2 pos, float2x4 t)
    {
        return float4((t._13_14 + (pos.x * t._11_12) + (pos.y * t._21_22)), t._23_24);
    }
}

//
//	Constant Buffer
//
cbuffer VSConstants2D : register(b0)
{
    row_major float2x4 g_transform;
    float4 g_colorMul;
}

cbuffer PSConstants2D : register(b0)
{
    float4 g_colorAdd;
    float4 g_sdfParam;
    float4 g_sdfOutlineColor;
    float4 g_sdfShadowColor;
    float4 g_internal;
}

ใพใšใ€ไธŠใฎใปใ†ใฎใ“ใฎใ‚ใŸใ‚Šใฎใ‚ณใƒผใƒ‰ใฏใ€Siv3Dใง2Dๆ็”ปใ™ใ‚‹ไธŠใงๅฟ…่ฆใชๅ…ฅๅŠ›ใƒฌใ‚คใ‚ขใ‚ฆใƒˆใ‚„ๅฎšๆ•ฐใƒใƒƒใƒ•ใ‚กใฎๅž‹ๅฎš็พฉใชใฎใงSiv3Dใงใ‚ซใ‚นใ‚ฟใƒ ใ‚ทใ‚งใƒผใƒ€ใƒผใ‚’ไฝฟใ†ๆ™‚ใฎใ‚ณใƒ”ใƒšใฎใ‚ˆใ†ใช้ƒจๅˆ†ใงใ™ใ€‚
(ใจใ„ใ†ใ‹ๅŸบๆœฌใฏใ‚ณใƒ”ใƒšใ—ใŸใปใ†ใŒใ‚ˆใ„ใงใ™)
(PSใ‚’ไฝฟใ‚ใชใ„ๅ ดๅˆใฏPSConstants2D ใฏไธ่ฆใงใ™)

ใŸใ ใ—ใ€ๆณจ็›ฎใ™ในใใจใ“ใ‚ใŒใ‚ใ‚Šใพใ™ใ€‚
ใใ‚ŒใฏVS Input (nothing)ใจใ‚ณใƒกใƒณใƒˆใ•ใ‚Œใฆใ„ใ‚‹ใ‚ˆใ†ใซใ€
้ ‚็‚นใฎๅ…ฅๅŠ›ๅž‹ๅฎš็พฉใŒใชใ„ใ“ใจใงใ™ใ€‚

ๆœฌๆฅTexture.drawใชใฉใงๆ็”ปใ™ใ‚‹้š›ใซใ‚ซใ‚นใ‚ฟใƒ ้ ‚็‚นใ‚ทใ‚งใƒผใƒ€ใƒผใ‚’ไฝฟใ†้š›ใซใฏ
ๅ„้ ‚็‚นใฎๅบงๆจ™ใ‚„uvใ€่‰ฒๆƒ…ๅ ฑใ‚’่จญๅฎšใ—ใฆๆ็”ปใ™ใ‚‹ใ‹ใ‚‰
ไปฅไธ‹ใฎใ‚ˆใ†ใชๅž‹ๅฎš็พฉใŒๅฟ…่ฆใงใ™ใ€‚

	struct VSInput
	{
		float2 position : POSITION;
		float2 uv : TEXCOORD0;
		float4 color : COLOR0;
	};

ใ—ใ‹ใ—ใ€DrawTrianglesใฏไธ€ๅˆ‡้ ‚็‚นๆƒ…ๅ ฑใ‚’่จญๅฎšใ›ใšใซใŸใ ใ€้ ‚็‚นๆ•ฐใ ใ‘(ไธ‰่ง’ๅฝขใฎๆ•ฐใ ใ‘)ๆŒ‡ๅฎšใ—ใฆๆ็”ปใ™ใ‚‹้–ขๆ•ฐใ ใฃใŸใฎใงใ€ใ“ใ“ใงใฏVSInputใŒไธ่ฆใซใชใ‚Šใพใ™ใ€‚


ๆฌกใซใƒ”ใ‚ฏใ‚ปใƒซใ‚ทใ‚งใƒผใƒ€ใƒผๅดใซ้–ขใ™ใ‚‹ใ‚ณใƒผใƒ‰ใงใ™ใ€‚
็‰นใซ็‰นๆฎŠใชใ“ใจใฏไฝ•ใ‚‚ใ—ใฆใ„ใพใ›ใ‚“ใฎใงใ€ใ‚นใƒซใƒผใ—ใพใ™ใ€‚

Texture2D       g_texture0 : register(t0);
SamplerState    g_sampler0 : register(s0);
------------------------

float4 PS(s3d::PSInput input) : SV_TARGET
{
    const float4 texColor = g_texture0.Sample(g_sampler0, input.uv);
    return (texColor * input.color) + g_colorAdd;
}

่ฃœ่ถณ๏ผšC++ๅดใงใŠ้ญšใ•ใ‚“ใฎใƒ†ใ‚ฏใ‚นใƒใƒฃใ‚’่จญๅฎšใ—ใฆใ„ใ‚‹ใฎใงโ†‘ใฎใจใ“ใ‚ใงใ‚ขใ‚ฏใ‚ปใ‚นใงใใ‚‹ๆ„Ÿใ˜ใงใ™
(ใ‚ตใƒณใƒ—ใƒฉใƒผใฏใ‚‚ใจใ‚‚ใจ่จญๅฎšใ•ใ‚Œใฆใ„ใ‚‹ใ‚‚ใฎใงๆง‹ใ‚ใชใ„ใฎใง็‰นใซๆ˜Ž็คบ็š„ใซ่จญๅฎšใ—ใฆใ„ใพใ›ใ‚“ใ€‚)

            // PSใงไฝฟใ†ใ‚ˆใ†ใซใƒ†ใ‚ฏใ‚นใƒใƒฃใ‚’ใ‚ปใƒƒใƒˆ
            s3d::Graphics2D::SetPSTexture(0, tex);

ใ•ใฆใ€ใ„ใ‚ˆใ„ใ‚ˆ้ ‚็‚นใ‚ทใ‚งใƒผใƒ€ใƒผใฎไธญใ‚’่ฆ‹ใฆใ„ใใพใ™ใ€‚

s3d::PSInput VS(uint id: SV_VERTEXID)

ใ“ใ“ใฎidใซใ€ๆ็”ปใ™ใ‚‹้ ‚็‚นๆ•ฐใฎๅˆ†ใ ใ‘ๆ•ฐๅ€คใŒๅ…ฅใฃใฆใใพใ™ใ€‚
ใคใพใ‚Šidใฏ
0 ~ DrawTrianglesใซๆธกใ—ใŸๅผ•ๆ•ฐใฎๆ•ฐ*3 - 1
ใพใงๆ•ฐๅญ—ใŒๅ…ฅใฃใฆใใพใ™ใ€‚(ไธ‰่ง’ๅฝขใฎ้ ‚็‚นๆ•ฐใฏ3ใชใฎใง*3ใ•ใ‚Œใพใ™ใ€‚)

    // ไธ€ๅŒนใฎใŠ้ญšใ•ใ‚“ใซๅฟ…่ฆใช้ ‚็‚นใฏ 6 
    const uint quadId = id / 6;

ๅ››่ง’ๅฝขใ‚’ๆ็”ปใ™ใ‚‹ใฎใซ้ ‚็‚นใŒ6ใคๅฟ…่ฆใชใฎใงไธ€ๅŒนใฎใŠ้ญšใ•ใ‚“ใ‚’่กจ็พใ™ใ‚‹ใฎใซ6้ ‚็‚นไฝฟใ„ใพใ™ใ€‚
ใชใฎใงใ€ใ“ใ“ใง6ใงๅ‰ฒใฃใฆใŠใใ“ใจใงใŠ้ญšใ•ใ‚“ไธ€ๅŒนใฎidใซๅค‰ๆ›ใ—ใฆใ„ใพใ™ใ€‚

    // ๅบงๆจ™ใ‚’้ฉๅฝ“ใซ่จˆ็ฎ—
    float2 pos = float2(0, 0);
    const uint sqrtFishCount = 1000;
    const int xId = (int)(quadId % sqrtFishCount);
    const int yId = (int)(quadId / sqrtFishCount);

    float2 size = float2(40.8, 38.4);
    pos += float2(xId * size.x, yId * size.y);

ใ“ใฎ่พบใฏๆœ€ๅˆใซๅฎ‰ๆ˜“ใชๅฎŸ่ฃ…ใ—ใŸๆ™‚ใจๅŒใ˜ใ‚ˆใ†ใซ้ฉๅฝ“ใซไธฆในใฆใ‚‹ใ ใ‘ใงใใ“ใพใง้‡่ฆใชใจใ“ใ‚ใงใฏใชใ„ใงใ™ใ€‚

float2 toUV(uint mod6)
{
    if (mod6 == 0) {
        return float2(0, 0);
    } else if (mod6 == 1) {
        return float2(1, 0);
    } else if (mod6 == 2) {
        return float2(0, 1);
    } else if (mod6 == 3) {
        return float2(0, 1);
    } else if (mod6 == 4) {
        return float2(1, 0);
    } else {
        return float2(1, 1);
    }
}

-----
    const uint mod6 = id % 6;
    // uvๅบงๆจ™ใ‚’่จˆ็ฎ—
    float2 uv = toUV(mod6);

ใŠ้ญšใ•ใ‚“ใฎใƒ†ใ‚ฏใ‚นใƒใƒฃใ‚’ๅผตใ‚Šไป˜ใ‘ใ‚‹ใŸใ‚ใซใฏๅ„้ ‚็‚นใซUVๅบงๆจ™ใ‚’่จญๅฎšใ™ใ‚‹ๅฟ…่ฆใŒใ‚ใ‚Šใพใ™ใ€‚
ใใฎใ‚ใŸใ‚Šใฎ่จˆ็ฎ—ใ‚’ใ“ใ“ใงใ—ใฆใ„ใพใ™ใ€‚

float2 toQuad(float2 uv, float2 size)
{
    float2 halfSize = size / 2.0;
    float2 ret = lerp(-halfSize, halfSize, uv);
    return ret;
}
-------
    // ๅ››่ง’ๅฝขใซใ™ใ‚‹
    pos += toQuad(uv, size);

ไธŠใฎใปใ†ใง้ฉๅฝ“ใซ่จˆ็ฎ—ใ—ใŸๅบงๆจ™ใŒไธญๅฟƒๅบงๆจ™ใจใชใ‚‹ๅ››่ง’ๅฝขใซใชใ‚‹ใ‚ˆใ†ใซ่จˆ็ฎ—ใ—ใฆใ„ใพใ™ใ€‚
(ใŠ้ญšใ•ใ‚“ไธ€ๅŒนใ‚’ๆ“ไฝœใ™ใ‚‹ใŸใ‚ใซ6ใงๅ‰ฒใฃใฆๅบงๆจ™่จˆ็ฎ—ใ‚’ใ—ใฆใ„ใŸใฎใงใ€ใ‚ณใ‚ณใ‚’ๅฟ˜ใ‚Œใ‚‹ใจ6้ ‚็‚นๅ…จ้ƒจๅŒใ˜ๅบงๆจ™ใซใชใฃใฆ็‚นใซใชใฃใฆใ—ใพใ„ใพใ™ใ€‚)

    s3d::PSInput result;
    result.position = s3d::Transform2D(pos, g_transform);
    result.uv = uv;
    result.color = g_colorMul;

ๆœ€ๅพŒใซใ€ไปŠใพใงใ„ใ‚ใ„ใ‚่จˆ็ฎ—ใ—ใŸใ‚‚ใฎใ‚’ใƒ”ใ‚ฏใ‚ปใƒซใ‚ทใ‚งใƒผใƒ€ใƒผใŒๆ‰ฑใ†ๅ…ฅๅŠ›ใฎๅฝขใซๅค‰ๆ›ใ—ใฆ็ต‚ใ‚ใ‚Šใงใ™ใ€‚

ใŠ้ญšใ•ใ‚“ใŒ100ไธ‡ไฝ“ๆณณใ„ใ 

๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ

๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ

ๅ…จใ็”ป้ขใซๅŽใพใ‚‹ใ‚ใ‘ใŒใชใ„ใฎใงใ™ใŒใ€100ไธ‡ไฝ“ๆณณใ„ใงใฆใ‚‚FPSใ‚‚็ถญๆŒใงใใฆใ„ใใ†ใงใ™ใ€‚
๐ŸŸ**ใ‚„ใฃใŸใญ!**๐ŸŸ

ใพใฆใ€ๆณณใ„ใงใชใ„ใ‚„ใชใ„ใ‹

ใใ†ใงใ™ใ€ใŠ้ญšใ•ใ‚“ใ€ใพใ ๆณณใ„ใงใพใ›ใ‚“โ€ฆ๏ผ๏ผ
็พ็Šถใ€ๅœๆญขใ—ใกใ‚ƒใฃใฆใ„ใพใ™ใ€‚
ใฉใ†ใ‚„ใฃใฆๆณณใŒใ™ใฎใ โ€ฆ๏ผŸ๏ผŸ๐ŸŸ

ๅฎšๆ•ฐใƒใƒƒใƒ•ใ‚ก

C++ๅดใ‹ใ‚‰ใ‚ทใ‚งใƒผใƒ€ใƒผใซใƒ‘ใƒฉใƒกใƒผใ‚ฟใ‚’้€ใ‚ŠใŸใ„ใจใใซไฝฟใˆใ‚‹ใฎใŒๅฎšๆ•ฐใƒใƒƒใƒ•ใ‚กใงใ™ใ€‚

Main.cpp
# include <Siv3D.hpp>

/// ๅฎšๆ•ฐใƒใƒƒใƒ•ใ‚กใฎๅž‹ๅฎš็พฉ
struct OsakanaSanParam
{
	float time{};
};

void Main()
{
	// ๐ŸŸใŠ้ญšใ•ใ‚“ใ‚’ๆณณใŒใ™ใž๏ฝž๏ฝž๐ŸŸ
	Texture tex(Emoji(U"๐ŸŸ"));

	// ๐ŸŸ 100ไธ‡ไฝ“ๆณณใŒใ™ใž๏ฝž๐ŸŸ
	constexpr size_t fishCount = 1000000;

	// ใ‚ทใ‚งใƒผใƒ€ใƒผ
	const FilePath shaderPath{ U"osakana_san.hlsl" };
	VertexShader vs = HLSL{ shaderPath };
	PixelShader ps = HLSL{ shaderPath };

	ConstantBuffer<OsakanaSanParam> cb;

	while (System::Update())
	{
		ClearPrint();
		Print << Profiler::FPS();
		Print << cb->time;

		// ๐ŸŸ ใŠ้ญšใ•ใ‚“ๆ็”ป๏ผ๏ผ๐ŸŸ
		{
			// ใ‚ทใ‚งใƒผใƒ€ใƒผ่จญๅฎš
			ScopedCustomShader2D scopedShder{ vs, ps };

			// ๅฎšๆ•ฐใƒใƒƒใƒ•ใ‚กใงๆ™‚้–“ใ‚’้€ใ‚‹
			cb->time = static_cast<float>(Scene::Time());
			s3d::Graphics2D::SetVSConstantBuffer(1, cb);

			// PSใงไฝฟใ†ใ‚ˆใ†ใซใƒ†ใ‚ฏใ‚นใƒใƒฃใ‚’ใ‚ปใƒƒใƒˆ
			s3d::Graphics2D::SetPSTexture(0, tex);

			// 100ไธ‡ * 2ๅ€‹ใฎไธ‰่ง’ๅฝขๆ็”ป
			// ๅ››่ง’ๅฝขใฎๆ็”ปใซใฏไธ‰่ง’ๅฝขใŒ2ใคใ„ใ‚‹ใฎใง2ๅ€ใซใ—ใฆใ‚‹
			s3d::Graphics2D::DrawTriangles(fishCount * 2);
		}
	}
}
osakana_san.hlsl
cbuffer OsakanasanParam : register(b1)
{
    float g_time;
}

s3d::PSInput VS(uint id: SV_VERTEXID)
{
    s3d::PSInput result;
    const uint quadId = id / 6;
    const uint mod6 = id % 6;

    float2 pos = float2(0, 0);
    const uint sqrtFishCount = 1000;
    const int xId = (int)(quadId % sqrtFishCount);
    const int yId = (int)(quadId / sqrtFishCount);

    float2 size = float2(40.8, 38.4);
    pos += float2(xId * size.x, yId * size.y);

    // ๆณณใ’ใŠ้ญšใ•ใ‚“๏ผ
    pos += float2(-100, -100) * g_time;

    float2 uv = toUV(mod6);
    pos += toQuad(uv, size);

    result.position = s3d::Transform2D(pos, g_transform);
    result.uv = uv;
    result.color = g_colorMul;

    return result;
}

ใ“ใฎใ‚ใŸใ‚Šใฎใ‚ณใƒผใƒ‰ใ‚’่ฟฝๅŠ ใ—ใพใ—ใŸใ€‚

/// ๅฎšๆ•ฐใƒใƒƒใƒ•ใ‚กใฎๅž‹ๅฎš็พฉ
struct OsakanaSanParam
{
	float time{};
};

------------

// ๅฎšๆ•ฐใƒใƒƒใƒ•ใ‚กใงๆ™‚้–“ใ‚’้€ใ‚‹
cb->time = static_cast<float>(Scene::Time());
s3d::Graphics2D::SetVSConstantBuffer(1, cb);
cbuffer OsakanasanParam : register(b1)
{
    float g_time;
}
--------

// ๆณณใ’ใŠ้ญšใ•ใ‚“๏ผ
pos += float2(-100, -100) * g_time;

C++ๅดใฎๅผ•ๆ•ฐ1ใจใ‚ทใ‚งใƒผใƒ€ใƒผๅดใฎb1ใฎๆ•ฐๅญ—ใ‚’ๅˆใ‚ใ›ใ‚‹ๅฟ…่ฆใŒใ‚ใ‚Šใพใ™ใ€‚

ใ›ใฃใ‹ใใชใฎใงใ€ใŠใพใ‘ใซใŠ้ญšใ•ใ‚“ใฎๅ‘ใใ‚‚ๅฐ‘ใ—ใ‹ใˆใพใ—ใ‚‡ใ†

float2 rot(float2 xy, float theta)
{
    float cosTheta = cos(theta);
    float sinTheta = sin(theta);
    return mul(float2x2(cosTheta, -sinTheta, sinTheta, cosTheta), xy);
}

float2 toQuad(float2 uv, float2 size)
{
    float2 halfSize = size / 2.0;
    float2 ret = lerp(-halfSize, halfSize, uv);

    // ๅ›ž่ปข
    {
        float theta = atan2(100.0, 100.0);
        ret = rot(ret, theta);
    }
    return ret;
}

๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ

๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ๐ŸŸ

๐ŸŸ**ใŠ้ญšใ•ใ‚“ๆณณใ„ใ ใ‚ˆ๏ผใ‚„ใฃใŸใญ!**๐ŸŸ

โš ๏ธ100ไธ‡ไฝ“ๆ็”ปใงใใ‚‹ใจใฏ่จ€ใฃใฆใชใ„

100ไธ‡ไฝ“ใฎใŠ้ญšใ•ใ‚“ใ‚’ๆณณใŒใ›ใ‚‹ใ“ใจใŒใงใใพใ—ใŸใ€ใŒใ€ๅฎŸใฏใ€100ไธ‡ไฝ“ใฎใŠ้ญšใ•ใ‚“ใŒๆ็”ปใงใใ‚‹ใ‚ใ‘ใงใฏใ‚ใ‚Šใพใ›ใ‚“ใ€‚
ใ“ใ‚Œใฏใ‚ฏใƒชใƒƒใƒ”ใƒณใ‚ฐๅ‡ฆ็†ใซใ‚ˆใ‚Šใ€็”ป้ขใซๆ˜ ใ‚‰ใชใ„ใ‚‚ใฎใฏๆจใฆใ‚‰ใ‚Œใฆใ„ใ‚‹ใŠใ‹ใ’ใงๅ‡ฆ็†ใŒ้ซ˜้€ŸๅŒ–ใ•ใ‚Œใฆใ„ใ‚‹ใŸใ‚ใงใ™ใ€‚

่ฉฆใ—ใซ100ไธ‡ๅŒนใ™ในใฆใŠใชใ˜ๅบงๆจ™ใซใ™ใ‚‹ใจ่‡ชๅˆ†ใฎ็’ฐๅขƒใงใฏใ‚ใกใ‚ƒใใกใ‚ƒๅ‡ฆ็†่ฝใกใ—ใพใ—ใŸใ€‚
(ใใ‚Œใงใ‚‚ๅฎ‰ๆ˜“ใซ100ไธ‡ๅ›žๆ็”ปๅ‘ฝไปคใ™ใ‚‹ใ‚ˆใ‚Šใฏๅ‡ฆ็†่ฒ ่ทใŒๅฐ‘ใชใ‹ใฃใŸ)

ใจใฏใ„ใˆใ€100ไธ‡ใฏ็„ก็†ใงใ‚‚10ไธ‡ๅŒนใใ‚‰ใ„ใชใ‚‰ๆ™ฎ้€šใซๆ็”ปใงใใกใ‚ƒใ„ใพใ—ใŸ!
(10ไธ‡ๅ›žๆ็”ปๅ‘ฝไปคใ—ใŸๅ ดๅˆใ‚‚ๅ‡ฆ็†่ฝใกใฏใ—ใฆใ„ใŸ)

ใŠใพใ‘๏ผš๐ŸŸ็งใฎใŠ้ญšใ•ใ‚“ใ‚’็ดนไป‹๐ŸŸ

ไปŠๅ›ž็ดนไป‹ใ—ใŸใ‚ฝใƒผใ‚นใ‚ณใƒผใƒ‰ใฏใ€ใ‚ใกใ‚ƒใใกใ‚ƒ็ถบ้บ—ใซๆ•ดๅˆ—ใ—ใŸใŠ้ญšใ•ใ‚“ใŒๆทกใ€…ใจ็งปๅ‹•ใ—ใฆใ„ใใ ใ‘ใงใ—ใŸใŒ
ใ‚‚ใฃใจใ„ใ‚ใ„ใ‚ๅ‘ณไป˜ใ‘ใ‚’ใ—ใฆใ„ใใจใ€ๆฅฝใ—ใ„ๆ„Ÿใ˜ใซใชใฃใฆใ„ใใพใ™ใ€‚
็งปๅ‹•ๅ‡ฆ็†่‡ชไฝ“ใ‚‚ใƒซโ€•ใƒ—ใ™ใ‚‹ใ‚ˆใ†ใซใ—ใŸใ‚Šใ™ใ‚‹ใจ็„ก้™ใซใŠ้ญšใ•ใ‚“ใŒๆณณใ„ใงใใ‚Œใพใ™ใ€‚
(ใ•ใฃใใฎๅฎŸ่ฃ…ใ ใจๆ™‚้–“็ตŒ้Žใซ้€ฃใ‚Œใฆๅบงๆจ™ใŒใฉใ‚“ใฉใ‚“ๆ›ดๆ–ฐใ•ใ‚Œใ‚‹ใฎใงใ€ใ„ใคใ‹ใŠ้ญšใ•ใ‚“ใŒใ„ใชใใชใฃใกใ‚ƒใ†ใ‹ใ‚‰ใญ)

โ€ปใชใŠใ€ใ•ใ™ใŒใซ100ไธ‡ไฝ“ใ‚‚ใŠใ‚ˆใŒใ—ใฆใ„ใพใ›ใ‚“ใ€‚๐ŸŸ

ๅ‚่€ƒ

ใ‚ซใ‚นใ‚ฟใƒ ใ‚ทใ‚งใƒผใƒ€ใƒผๅ‘จใ‚ŠใฏOpenSiv3Dใฎใƒใƒฅใƒผใƒˆใƒชใ‚ขใƒซใซใ‚ใ‚‹ใ‚‚ใฎใ‚’่ชญใ‚€ใฎใŒใ„ใ„ใจๆ€ใ„ใพใ™ใ€‚

ใพใจใ‚

  • s3d::Graphics2D::DrawTriangles(uint32 count)ใ‚’ไฝฟใ†ใจใ€ๅ‡ฆ็†่ฒ ่ทใ‚’ใŠใ•ใˆใคใคๆฒขๅฑฑใฎ้ ‚็‚นใ‚’ๆ‰ฑใ†ใ“ใจใŒใงใใ‚‹
    • ใŸใ ใ—้ ‚็‚นใ‚ทใ‚งใƒผใƒ€ใƒผใง่‡ชๅ‰ใซๅ…จใฆ่จˆ็ฎ—ใ™ใ‚‹ๅฟ…่ฆใŒใ‚ใ‚‹
    • ่ค‡้›‘ใชๅฝข็Šถใ‚’ๆ็”ปใ—ใŸใ„้š›ใฎ้ ‚็‚น่จˆ็ฎ—ใซไพฟๅˆฉใงใ™
    • ไปŠๅ›žใฎใ‚ˆใ†ใซๅŒใ˜ใƒ†ใ‚ฏใ‚นใƒใƒฃใชใฉใ‚’ๅคง้‡ใซ็”ป้ขใซๅ‡บใ—ใŸใ„ใจใใชใฉใซใฏไฝŽใ‚ณใ‚นใƒˆใงใŸใใ•ใ‚“ๆ็”ปใงใใฆไพฟๅˆฉใงใ™
  • ใŠ้ญšใ•ใ‚“ใŒใ„ใฃใฑใ„ๆณณใ„ใงใฆๅฏๆ„›ใ„๐ŸŸ
  • ๆฐดๆ—้คจใซ่กŒใใŸใ„
9
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
9
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?