#include "StageDrawer.h"
#include "GameMap.h"
#include "main.h"
StageDrawer::~StageDrawer()
{
	pRenderer->ClearBuffer(&stageBuffer);
	pRenderer->ClearBuffer(&entityLight);
}

void StageDrawer::Init(MyDX11Renderer* pRenderer, MyView* pView, GameMap* gameMap, EntityRes* entityRes, GamePxa* gamePxa)
{
	this->pRenderer = pRenderer;
	this->pView = pView;
	this->gameMap = gameMap;
	this->entityRes = entityRes;
	this->gamePxa = gamePxa;
	mapDrawer.Init(pRenderer, pView, gamePxa);
}

void StageDrawer::Step()
{
	timeCounter_mapLoopBk++;

	windAniIndex_set_last = windAniIndex_set;
	windAniIndex_set += windAniSpeed;
	if (windAniIndex_set >= 1)
	{
		windAniIndex_set -= 1;
		windAniIndex_set_last = windAniIndex_set - windAniSpeed;
	}
	windAniIndex2_set_last = windAniIndex2_set;
	windAniIndex2_set += windAniSpeed2;
	if (windAniIndex2_set >= 1)
	{
		windAniIndex2_set -= 1;
		windAniIndex2_set_last = windAniIndex2_set - windAniSpeed2;
	}
	for (auto& layer : *gameMap->GetLayerList())
	{
		if (!layer.visible)
			continue;
		if (layer.layerType == 2)
			mapDrawer.LoopLayerStep(&layer, timeCounter_mapLoopBk);
	}
}

MyMapLayer* StageDrawer::Draw(float deltaTime)
{
	pRenderer->GameSetScale(pView->scale);
	pRenderer->GameSetOffset(pView->offX, pView->offY);
	auto lastRTV = pRenderer->GetPenRTV();
	float windAniIndex = lerp(windAniIndex_set_last, windAniIndex_set, deltaTime);
	float windAniIndex2 = lerp(windAniIndex2_set_last, windAniIndex2_set, deltaTime);
	/*----------------------------标记所有的灯光实体--------------------------*/
	entityRes->ClearLightList();
	for (auto& layer : *gameMap->GetLayerList())
	{
		if (!layer.visible)
			continue;
		entityRes->MarkLightEntity(&layer);
	}
	/*----------------------------分层绘制--------------------------*/
	for (auto& layer : *gameMap->GetLayerList())
	{
		if (!layer.visible)
			continue;
		if (layer.pxaName == L"null")
		{
			layer.pxaName = L"null";
		}
		if (layer.dayLight == 1)//优化，天光为1时不需要渲染光影
		{
			switch (layer.layerType)
			{
			case 0://主层
			case 1://背景层
				mapDrawer.DrawLayerBack(&layer, windAniIndex, windAniIndex2);
				entityRes->DrawEntityLayer(&layer);
				mapDrawer.DrawLayerFront(&layer);
				break;
			case 2://循环背景层
				mapDrawer.DrawLoopLayer(&layer, deltaTime);
				entityRes->DrawEntityLayer(&layer);
				break;
			}
			continue;
		}
		/*-------------------------绘制舞台到stageBuffer--------------------------*/
		pRenderer->SetPenRTV(stageBuffer.pRTV);
		pRenderer->RenderClearRTV(stageBuffer.pRTV);
		switch (layer.layerType)
		{
		case 0://主层
		case 1://背景层
			mapDrawer.DrawLayerBack(&layer, windAniIndex, windAniIndex2);
			entityRes->DrawEntityLayer(&layer);
			mapDrawer.DrawLayerFront(&layer);
			break;
		case 2://循环背景层
			mapDrawer.DrawLoopLayer(&layer, deltaTime);
			entityRes->DrawEntityLayer(&layer);
			break;
		}
		/*-------------------------设置天光--------------------------*/
		pRenderer->GameSetDayLight(layer.dayLight);
		pRenderer->GameSetHSV(layer.tinyHSV[0], layer.tinyHSV[1], layer.tinyHSV[2]);
		/*-------------------------绘制发光实体--------------------------*/
		//绘制发光实体到entityLight
		//pRenderer->SetBlendMode_Add();
		pRenderer->SetPenRTV(entityLight.pRTV);
		pRenderer->RenderClearRTV(entityLight.pRTV, 1.0f, 1.0f, 1.0f, 0.0f);
		entityRes->DrawLightEntity(&layer);
		//pRenderer->SetBlendMode_Default();
		/*-------------------------最终输出--------------------------*/
		//entityLight、stageBuffer
		pRenderer->SetPenRTV(lastRTV);
		auto vs = entityRes->GetVertexShader(L"sys_finalLight");
		auto ps = entityRes->GetPixelShader(L"sys_finalLight");
		pRenderer->SetTPenVertexShader(vs);
		pRenderer->SetTPenPixelShader(ps);
		pRenderer->SetTPenDraw(entityLight.pSRV, stageBuffer.pSRV);
		pRenderer->AddRenderCopy();
		pRenderer->DrawRenderCopy();
		//复原着色器
		pRenderer->SetTPenVertexShader();
		pRenderer->SetTPenPixelShader();
	}
	for (auto& layer : *gameMap->GetLayerList())
		if (layer.layerType == 0)
			return &layer;
	//该房间没有主层（游戏错误）
	wchar_t err[MAX_PATH];
	swprintf_s(err, L"游戏地图%s错误", gameMap->GetMapFileName().c_str());
	MessageBoxW(hwnd, err, L"该房间没有设置主层", MB_ICONERROR);
	exit(0);
	return nullptr;
}

void StageDrawer::OnResetScale(int w, int h)
{
	if (pRenderer)
	{
		pRenderer->SetBufferSize((UINT)w, (UINT)h, &stageBuffer, "stageBuffer");
		pRenderer->SetBufferSize((UINT)w, (UINT)h, &entityLight, "entityLight");
		mapDrawer.OnResetScale();
	}
}

void StageDrawer::Reset()
{
	timeCounter_mapLoopBk = 0;
	windAniIndex_set = windAniIndex_set_last = 0;
	windAniIndex2_set = windAniIndex2_set_last = 0;
	mapDrawer.Reset();
}

MapDrawer* StageDrawer::GetMapDrawer()
{
	return &mapDrawer;
}
