OverdriveArenaWear.cs
using Sandbox;
using System;
namespace PaintballBaddies;
// Native impact definitions add battle wear while the existing masonry chips,
// traffic grime and column rust remain. Original arena art is left recoverable.
public sealed class OverdriveArenaWear : Component
{
private GameObject overlay;
private float ready;
public int Scars {get;private set;}
protected override void OnUpdate()
{
bool active=MultiplayerSession.Find(Scene)?.IsOverdrive==true;
if(overlay.IsValid()){overlay.Enabled=active;return;}
ready+=Time.Delta;
if(!active || ready<2 || Scene.GetAllComponents<MapInstance>().Any(m=>m.Active && !m.IsLoaded))return;
overlay=new GameObject(GameObject,true,"Overdrive battle scarring"){NetworkMode=NetworkMode.Never};
var points=ArenaMap.PatrolPoints(Scene);if(points.Length==0)points=ArenaOpponent.CreatePatrolRoute();
var random=new Random(92126);float R(float a,float b)=>a+(float)random.NextDouble()*(b-a);
foreach(var point in points)
{
for(int i=0;i<6 && Scars<72;i++)
{
var from=point+Vector3.Up*R(28,115);var direction=Rotation.FromYaw(i*60+R(-20,20)).Forward;
var hit=Scene.Trace.Ray(from,from+direction*1400).WithoutTags("paintball_actor","paintball_debris","pop_target","overdrive_enemy").Run();
if(!hit.Hit || MathF.Abs(hit.Normal.z)>.6f)continue;
var metal=hit.Surface?.ResourcePath?.Contains("metal")==true;
bool scorch=Scars%7==0;
var path=scorch ? "decals/scorchmarks/decal_scorchmark_01.decal" : metal ? "decals/impact/metal/decal_impact_metal_01.decal" : "decals/impact/concrete/decal_impact_concrete_04.decal";
var definition=ResourceLibrary.Get<DecalDefinition>(path);if(definition is null)continue;
var mark=new GameObject(overlay,true,scorch ? "Electrical scorch" : metal ? "Dented metal" : "Chipped concrete impact")
{WorldPosition=hit.HitPosition+hit.Normal*.2f,WorldRotation=Rotation.LookAt(-hit.Normal)};
var decal=mark.Components.Create<Decal>();decal.Decals=[definition];decal.Size=Vector2.One;
decal.Scale=scorch ? R(.3f,.6f) : R(1.1f,2.8f);decal.Depth=8;decal.Rotation=R(0,360);
decal.ColorTint=scorch ? new Color(.55f,.5f,.45f,.7f) : new Color(.7f,.67f,.62f,.85f);
decal.LifeTime=0;decal.Transient=false;decal.SortLayer=8;Scars++;
}
}
}
protected override void OnDestroy(){overlay?.Destroy();}
}