mirror of
https://github.com/ZDoom/gzdoom.git
synced 2024-11-10 06:42:08 +00:00
Add corona actor
This commit is contained in:
parent
4710a40fb5
commit
50d16c75d9
10 changed files with 226 additions and 0 deletions
|
@ -920,6 +920,7 @@ set (PCH_SOURCES
|
|||
playsim/mapthinkers/dsectoreffect.cpp
|
||||
playsim/a_pickups.cpp
|
||||
playsim/a_action.cpp
|
||||
playsim/a_corona.cpp
|
||||
playsim/a_decals.cpp
|
||||
playsim/a_dynlight.cpp
|
||||
playsim/a_flashfader.cpp
|
||||
|
|
|
@ -863,3 +863,5 @@ xx(lm_sampledist_ceiling)
|
|||
xx(lm_suncolor)
|
||||
xx(lm_sampledistance)
|
||||
xx(lm_gridsize)
|
||||
|
||||
xx(Corona)
|
||||
|
|
32
src/playsim/a_corona.cpp
Normal file
32
src/playsim/a_corona.cpp
Normal file
|
@ -0,0 +1,32 @@
|
|||
/*
|
||||
** Light Coronas
|
||||
** Copyright (c) 2022 Nash Muhandes, Magnus Norddahl
|
||||
**
|
||||
** This software is provided 'as-is', without any express or implied
|
||||
** warranty. In no event will the authors be held liable for any damages
|
||||
** arising from the use of this software.
|
||||
**
|
||||
** Permission is granted to anyone to use this software for any purpose,
|
||||
** including commercial applications, and to alter it and redistribute it
|
||||
** freely, subject to the following restrictions:
|
||||
**
|
||||
** 1. The origin of this software must not be misrepresented; you must not
|
||||
** claim that you wrote the original software. If you use this software
|
||||
** in a product, an acknowledgment in the product documentation would be
|
||||
** appreciated but is not required.
|
||||
** 2. Altered source versions must be plainly marked as such, and must not be
|
||||
** misrepresented as being the original software.
|
||||
** 3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
|
||||
|
||||
#include "actor.h"
|
||||
#include "a_corona.h"
|
||||
#include "a_dynlight.h"
|
||||
|
||||
IMPLEMENT_CLASS(ACorona, false, false)
|
||||
|
||||
void ACorona::Tick()
|
||||
{
|
||||
Super::Tick();
|
||||
}
|
38
src/playsim/a_corona.h
Normal file
38
src/playsim/a_corona.h
Normal file
|
@ -0,0 +1,38 @@
|
|||
/*
|
||||
** Light Coronas
|
||||
** Copyright (c) 2022 Nash Muhandes, Magnus Norddahl
|
||||
**
|
||||
** This software is provided 'as-is', without any express or implied
|
||||
** warranty. In no event will the authors be held liable for any damages
|
||||
** arising from the use of this software.
|
||||
**
|
||||
** Permission is granted to anyone to use this software for any purpose,
|
||||
** including commercial applications, and to alter it and redistribute it
|
||||
** freely, subject to the following restrictions:
|
||||
**
|
||||
** 1. The origin of this software must not be misrepresented; you must not
|
||||
** claim that you wrote the original software. If you use this software
|
||||
** in a product, an acknowledgment in the product documentation would be
|
||||
** appreciated but is not required.
|
||||
** 2. Altered source versions must be plainly marked as such, and must not be
|
||||
** misrepresented as being the original software.
|
||||
** 3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "actor.h"
|
||||
|
||||
EXTERN_CVAR(Bool, gl_coronas)
|
||||
|
||||
class AActor;
|
||||
|
||||
class ACorona : public AActor
|
||||
{
|
||||
DECLARE_CLASS(ACorona, AActor)
|
||||
|
||||
public:
|
||||
void Tick();
|
||||
|
||||
float CoronaFade = 0.0f;
|
||||
};
|
|
@ -44,6 +44,8 @@
|
|||
#include "hw_vrmodes.h"
|
||||
#include "hw_clipper.h"
|
||||
#include "v_draw.h"
|
||||
#include "a_corona.h"
|
||||
#include "texturemanager.h"
|
||||
|
||||
EXTERN_CVAR(Float, r_visibility)
|
||||
CVAR(Bool, gl_bandedswlight, false, CVAR_ARCHIVE)
|
||||
|
@ -55,6 +57,8 @@ CVAR(Bool, gl_texture, true, 0)
|
|||
CVAR(Float, gl_mask_threshold, 0.5f, CVAR_ARCHIVE | CVAR_GLOBALCONFIG)
|
||||
CVAR(Float, gl_mask_sprite_threshold, 0.5f, CVAR_ARCHIVE | CVAR_GLOBALCONFIG)
|
||||
|
||||
CVAR(Bool, gl_coronas, true, CVAR_ARCHIVE);
|
||||
|
||||
sector_t * hw_FakeFlat(sector_t * sec, sector_t * dest, area_t in_area, bool back);
|
||||
|
||||
//==========================================================================
|
||||
|
@ -165,6 +169,7 @@ void HWDrawInfo::StartScene(FRenderViewpoint &parentvp, HWViewpointUniforms *uni
|
|||
|
||||
for (int i = 0; i < GLDL_TYPES; i++) drawlists[i].Reset();
|
||||
hudsprites.Clear();
|
||||
Coronas.Clear();
|
||||
vpIndex = 0;
|
||||
|
||||
// Fullbright information needs to be propagated from the main view.
|
||||
|
@ -569,6 +574,128 @@ void HWDrawInfo::RenderPortal(HWPortal *p, FRenderState &state, bool usestencil)
|
|||
|
||||
}
|
||||
|
||||
void HWDrawInfo::DrawCorona(FRenderState& state, ACorona* corona, double dist)
|
||||
{
|
||||
spriteframe_t* sprframe = &SpriteFrames[sprites[corona->sprite].spriteframes + (size_t)corona->SpawnState->GetFrame()];
|
||||
FTextureID patch = sprframe->Texture[0];
|
||||
if (!patch.isValid()) return;
|
||||
auto tex = TexMan.GetGameTexture(patch, false);
|
||||
if (!tex || !tex->isValid()) return;
|
||||
|
||||
// Project the corona sprite center
|
||||
FVector4 worldPos((float)corona->X(), (float)corona->Z(), (float)corona->Y(), 1.0f);
|
||||
FVector4 viewPos, clipPos;
|
||||
VPUniforms.mViewMatrix.multMatrixPoint(&worldPos[0], &viewPos[0]);
|
||||
VPUniforms.mProjectionMatrix.multMatrixPoint(&viewPos[0], &clipPos[0]);
|
||||
if (clipPos.W < -1.0f) return; // clip z nearest
|
||||
float halfViewportWidth = screen->GetWidth() * 0.5f;
|
||||
float halfViewportHeight = screen->GetHeight() * 0.5f;
|
||||
float invW = 1.0f / clipPos.W;
|
||||
float screenX = halfViewportWidth + clipPos.X * invW * halfViewportWidth;
|
||||
float screenY = halfViewportHeight - clipPos.Y * invW * halfViewportHeight;
|
||||
|
||||
float alpha = corona->CoronaFade * float(corona->Alpha);
|
||||
|
||||
// distance-based fade - looks better IMO
|
||||
float distNearFadeStart = float(corona->RenderRadius()) * 0.1f;
|
||||
float distFarFadeStart = float(corona->RenderRadius()) * 0.5f;
|
||||
float distFade = 1.0f;
|
||||
|
||||
if (float(dist) < distNearFadeStart)
|
||||
distFade -= abs(((float(dist) - distNearFadeStart) / distNearFadeStart));
|
||||
else if (float(dist) >= distFarFadeStart)
|
||||
distFade -= (float(dist) - distFarFadeStart) / distFarFadeStart;
|
||||
|
||||
alpha *= distFade;
|
||||
|
||||
state.SetColorAlpha(0xffffff, alpha, 0);
|
||||
if (isSoftwareLighting()) state.SetSoftLightLevel(255);
|
||||
else state.SetNoSoftLightLevel();
|
||||
|
||||
state.SetLightIndex(-1);
|
||||
state.SetRenderStyle(corona->RenderStyle);
|
||||
state.SetTextureMode(corona->RenderStyle);
|
||||
|
||||
state.SetMaterial(tex, UF_Sprite, CTF_Expand, CLAMP_XY_NOMIP, 0, 0);
|
||||
|
||||
float scale = screen->GetHeight() / 1000.0f;
|
||||
float tileWidth = corona->Scale.X * tex->GetDisplayWidth() * scale;
|
||||
float tileHeight = corona->Scale.Y * tex->GetDisplayHeight() * scale;
|
||||
float x0 = screenX - tileWidth, y0 = screenY - tileHeight;
|
||||
float x1 = screenX + tileWidth, y1 = screenY + tileHeight;
|
||||
|
||||
float u0 = 0.0f, v0 = 0.0f;
|
||||
float u1 = 1.0f, v1 = 1.0f;
|
||||
|
||||
auto vert = screen->mVertexData->AllocVertices(4);
|
||||
auto vp = vert.first;
|
||||
unsigned int vertexindex = vert.second;
|
||||
|
||||
vp[0].Set(x0, y0, 1.0f, u0, v0);
|
||||
vp[1].Set(x1, y0, 1.0f, u1, v0);
|
||||
vp[2].Set(x0, y1, 1.0f, u0, v1);
|
||||
vp[3].Set(x1, y1, 1.0f, u1, v1);
|
||||
|
||||
state.Draw(DT_TriangleStrip, vertexindex, 4);
|
||||
}
|
||||
|
||||
static ETraceStatus CheckForViewpointActor(FTraceResults& res, void* userdata)
|
||||
{
|
||||
FRenderViewpoint* data = (FRenderViewpoint*)userdata;
|
||||
if (res.HitType == TRACE_HitActor && res.Actor && res.Actor == data->ViewActor)
|
||||
{
|
||||
return TRACE_Skip;
|
||||
}
|
||||
|
||||
return TRACE_Stop;
|
||||
}
|
||||
|
||||
|
||||
void HWDrawInfo::DrawCoronas(FRenderState& state)
|
||||
{
|
||||
state.EnableDepthTest(false);
|
||||
state.SetDepthMask(false);
|
||||
|
||||
HWViewpointUniforms vp = VPUniforms;
|
||||
vp.mViewMatrix.loadIdentity();
|
||||
vp.mProjectionMatrix = VRMode::GetVRMode(true)->GetHUDSpriteProjection();
|
||||
screen->mViewpoints->SetViewpoint(state, &vp);
|
||||
|
||||
float timeElapsed = (screen->FrameTime - LastFrameTime) / 1000.0f;
|
||||
LastFrameTime = screen->FrameTime;
|
||||
|
||||
for (ACorona* corona : Coronas)
|
||||
{
|
||||
DVector3 direction = Viewpoint.Pos - corona->Pos();
|
||||
double dist = direction.Length();
|
||||
|
||||
// skip coronas that are too far
|
||||
if (dist > corona->RenderRadius())
|
||||
continue;
|
||||
|
||||
static const float fadeSpeed = 9.0f;
|
||||
|
||||
direction.MakeUnit();
|
||||
FTraceResults results;
|
||||
if (!Trace(corona->Pos(), corona->Sector, direction, dist, MF_SOLID, ML_BLOCKEVERYTHING, corona, results, 0, CheckForViewpointActor, &Viewpoint))
|
||||
{
|
||||
corona->CoronaFade = std::min(corona->CoronaFade + timeElapsed * fadeSpeed, 1.0f);
|
||||
}
|
||||
else
|
||||
{
|
||||
corona->CoronaFade = std::max(corona->CoronaFade - timeElapsed * fadeSpeed, 0.0f);
|
||||
}
|
||||
|
||||
if (corona->CoronaFade > 0.0f)
|
||||
DrawCorona(state, corona, dist);
|
||||
}
|
||||
|
||||
state.SetTextureMode(TM_NORMAL);
|
||||
screen->mViewpoints->Bind(state, vpIndex);
|
||||
state.EnableDepthTest(true);
|
||||
state.SetDepthMask(true);
|
||||
}
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
//
|
||||
// Draws player sprites and color blend
|
||||
|
@ -580,6 +707,11 @@ void HWDrawInfo::EndDrawScene(sector_t * viewsector, FRenderState &state)
|
|||
{
|
||||
state.EnableFog(false);
|
||||
|
||||
if (gl_coronas && Coronas.Size() > 0)
|
||||
{
|
||||
DrawCoronas(state);
|
||||
}
|
||||
|
||||
// [BB] HUD models need to be rendered here.
|
||||
const bool renderHUDModel = IsHUDModelForPlayerAvailable(players[consoleplayer].camera->player);
|
||||
if (renderHUDModel)
|
||||
|
|
|
@ -29,6 +29,7 @@ class IShadowMap;
|
|||
struct particle_t;
|
||||
struct FDynLightData;
|
||||
struct HUDSprite;
|
||||
class ACorona;
|
||||
class Clipper;
|
||||
class HWPortal;
|
||||
class FFlatVertexBuffer;
|
||||
|
@ -150,6 +151,8 @@ struct HWDrawInfo
|
|||
TArray<HWPortal *> Portals;
|
||||
TArray<HWDecal *> Decals[2]; // the second slot is for mirrors which get rendered in a separate pass.
|
||||
TArray<HUDSprite> hudsprites; // These may just be stored by value.
|
||||
TArray<ACorona*> Coronas;
|
||||
uint64_t LastFrameTime = 0;
|
||||
|
||||
TArray<MissingTextureInfo> MissingUpperTextures;
|
||||
TArray<MissingTextureInfo> MissingLowerTextures;
|
||||
|
@ -300,6 +303,8 @@ public:
|
|||
|
||||
void DrawDecals(FRenderState &state, TArray<HWDecal *> &decals);
|
||||
void DrawPlayerSprites(bool hudModelStep, FRenderState &state);
|
||||
void DrawCoronas(FRenderState& state);
|
||||
void DrawCorona(FRenderState& state, ACorona* corona, double dist);
|
||||
|
||||
void ProcessLowerMinisegs(TArray<seg_t *> &lowersegs);
|
||||
void AddSubsectorToPortal(FSectorPortalGroup *portal, subsector_t *sub);
|
||||
|
|
|
@ -33,6 +33,7 @@
|
|||
#include "r_sky.h"
|
||||
#include "r_utility.h"
|
||||
#include "a_pickups.h"
|
||||
#include "a_corona.h"
|
||||
#include "d_player.h"
|
||||
#include "g_levellocals.h"
|
||||
#include "events.h"
|
||||
|
@ -703,6 +704,12 @@ void HWSprite::Process(HWDrawInfo *di, AActor* thing, sector_t * sector, area_t
|
|||
return;
|
||||
}
|
||||
|
||||
if (thing->IsKindOf(NAME_Corona))
|
||||
{
|
||||
di->Coronas.Push(static_cast<ACorona*>(thing));
|
||||
return;
|
||||
}
|
||||
|
||||
const auto &vp = di->Viewpoint;
|
||||
AActor *camera = vp.camera;
|
||||
|
||||
|
|
|
@ -2637,6 +2637,7 @@ OptionMenu "OpenGLOptions" protected
|
|||
Option "$GLPREFMNU_SPRBILLFACECAMERA", gl_billboard_faces_camera, "OnOff"
|
||||
Option "$GLPREFMNU_PARTICLESTYLE", gl_particles_style, "Particles"
|
||||
Option "$GLPREFMNU_RENDERQUALITY", gl_seamless, "Precision"
|
||||
Option "$GLPREFMNU_CORONAS", gl_coronas, "OnOff"
|
||||
StaticText " "
|
||||
Slider "$GLPREFMNU_MENUBLUR", gl_menu_blur, 0, 5.0, 0.5, 2
|
||||
StaticText " "
|
||||
|
|
|
@ -92,6 +92,7 @@ version "4.9"
|
|||
#include "zscript/actors/shared/fastprojectile.zs"
|
||||
#include "zscript/actors/shared/randomspawner.zs"
|
||||
#include "zscript/actors/shared/dynlights.zs"
|
||||
#include "zscript/actors/shared/corona.zs"
|
||||
|
||||
#include "zscript/actors/doom/doomplayer.zs"
|
||||
#include "zscript/actors/doom/possessed.zs"
|
||||
|
|
7
wadsrc/static/zscript/actors/shared/corona.zs
Normal file
7
wadsrc/static/zscript/actors/shared/corona.zs
Normal file
|
@ -0,0 +1,7 @@
|
|||
class Corona : Actor native
|
||||
{
|
||||
Default
|
||||
{
|
||||
RenderRadius 1024.0;
|
||||
}
|
||||
}
|
Loading…
Reference in a new issue