39 string m_Name =
"Default setup";
45 float m_PositiveHeight = 25;
46 float m_NegativeHeight = 10;
51 int m_InnerSpacing = 35;
53 bool m_OuterRingToggle =
true;
54 int m_OuterRingOffset = -5;
55 int m_OuterSpacing = 20;
57 int m_VerticalLayers = 0;
58 int m_VerticalOffset = 10;
61 int m_ParticleID =
ParticleList.CONTAMINATED_AREA_GAS_BIGASS;
62 int m_AroundParticleID =
ParticleList.CONTAMINATED_AREA_GAS_AROUND;
63 int m_TinyParticleID =
ParticleList.CONTAMINATED_AREA_GAS_TINY;
64 string m_PPERequesterType;
65 int m_PPERequesterIdx = -1;
66 int m_EffectsPriority;
69 string m_TriggerType =
"ContaminatedTrigger";
81 RegisterNetSyncVariableFloat(
"m_Radius", 0, 0, 2);
82 RegisterNetSyncVariableFloat(
"m_PositiveHeight", 0, 0, 2);
83 RegisterNetSyncVariableFloat(
"m_NegativeHeight", 0, 0, 2);
85 RegisterNetSyncVariableInt(
"m_InnerRings");
86 RegisterNetSyncVariableInt(
"m_InnerSpacing");
87 RegisterNetSyncVariableInt(
"m_OuterRingOffset");
88 RegisterNetSyncVariableInt(
"m_OuterSpacing");
89 RegisterNetSyncVariableInt(
"m_VerticalLayers");
90 RegisterNetSyncVariableInt(
"m_VerticalOffset");
92 RegisterNetSyncVariableInt(
"m_ParticleID");
98 RegisterNetSyncVariableBool(
"m_OuterRingToggle");
106 void SetupZoneData( EffectAreaParams params )
109 if ( params.m_ParamName !=
"" )
110 m_Name = params.m_ParamName;
111 if ( params.m_ParamTriggerType !=
"" )
112 m_TriggerType = params.m_ParamTriggerType;
114 if ( params.m_ParamRadius > 0 )
116 if ( params.m_ParamPosHeight > -1 )
117 m_PositiveHeight = params.m_ParamPosHeight;
118 if ( params.m_ParamNegHeight > -1 )
119 m_NegativeHeight = params.m_ParamNegHeight;
121 m_InnerRings = params.m_ParamInnerRings;
122 if ( params.m_ParamInnerSpace > -1 )
123 m_InnerSpacing = params.m_ParamInnerSpace;
125 m_OuterRingToggle = params.m_ParamOuterToggle;
126 if ( params.m_ParamOuterSpace > -1 )
127 m_OuterSpacing = params.m_ParamOuterSpace;
128 m_OuterRingOffset = params.m_ParamOuterOffset;
130 if ( params.m_ParamVertLayers > 0 )
131 m_VerticalLayers = params.m_ParamVertLayers;
132 if ( params.m_ParamVerticalOffset > 0 )
133 m_VerticalOffset = params.m_ParamVerticalOffset;
135 m_ParticleID = params.m_ParamPartId;
136 m_AroundParticleID = params.m_ParamAroundPartId;
137 m_TinyParticleID = params.m_ParamTinyPartId;
139 if ( params.m_ParamPpeRequesterType !=
"" )
141 m_PPERequesterType = params.m_ParamPpeRequesterType;
142 m_PPERequesterIdx = GetRequesterIndex(m_PPERequesterType);
162 override void OnCEUpdate()
175 if ( !
GetGame().IsDedicatedServer() )
190 void InitZoneServer() {};
192 void InitZoneClient() {};
198 override bool CanPutInCargo(
EntityAI parent )
203 override bool CanPutIntoHands(
EntityAI parent )
208 override bool DisableVicinityIcon()
213 override bool CanBeTargetedByAI(
EntityAI ai )
222 void PlaceParticles(
vector pos,
float radius,
int nbRings,
int innerSpacing,
bool outerToggle,
int outerSpacing,
int outerOffset,
int partId )
229 Error(
"[WARNING] :: [EffectArea PlaceParticles] :: no particle defined, skipping area particle generation" );
233 bool snapFirstLayer =
true;
235 snapFirstLayer =
false;
242 Error(
"[WARNING] :: [EffectArea PlaceParticles] :: Radius of contaminated zone is set to 0, this should not happen");
246 if ( outerToggle && radius == outerOffset )
248 Error(
"[WARNING] :: [EffectArea PlaceParticles] :: Your outerOffset is EQUAL to your Radius, this will result in division by 0");
253 if ( innerSpacing == 0 )
259 int numberOfEmitters = 1;
266 ParticlePropertiesArray props =
new ParticlePropertiesArray();
269 for (
int k = 0; k <= m_VerticalLayers; k++ )
276 partPos[1] = partPos[1] + ( m_VerticalOffset * k );
280 props.Insert(ParticleProperties(partPos, ParticlePropertiesFlags.PLAY_ON_CREATION,
null,
vector.Zero,
this));
284 for (
int i = 1; i <= nbRings + outerToggle; i++ )
289 float angleIncrement;
297 ab = radius - outerOffset;
300 angleIncrement =
Math.Acos( 1 - ( ( outerSpacing * outerSpacing ) / ( 2 *
Math.SqrInt(ab) ) ) );
301 temp[2] = temp[2] + ab;
307 ab = ( radius / ( nbRings + 1 ) ) * i;
310 angleIncrement =
Math.Acos( 1 - ( ( innerSpacing * innerSpacing ) / ( 2 *
Math.SqrInt(ab) ) ) );
311 temp[2] = temp[2] + ab;
316 for (
int j = 0; j <= (
Math.PI2 / angleIncrement ); j++ )
322 float sinAngle =
Math.Sin( angle );
323 float cosAngle =
Math.Cos( angle );
325 partPos =
vector.RotateAroundZero( temp,
vector.Up, cosAngle, sinAngle );
329 if ( k == 0 && snapFirstLayer ==
true )
330 partPos[1] =
GetGame().SurfaceY( partPos[0], partPos[2] );
331 else if ( k == 0 && snapFirstLayer ==
false )
332 partPos[1] = partPos[1] - m_NegativeHeight;
335 if ( partPos[1] <= pos[1] + m_PositiveHeight && partPos[1] >= pos[1] - m_NegativeHeight )
338 props.Insert(ParticleProperties(partPos, ParticlePropertiesFlags.PLAY_ON_CREATION,
null,
GetGame().GetSurfaceOrientation( partPos[0], partPos[2] ),
this));
344 angle += angleIncrement;
351 m_ToxicClouds.Reserve(partCounter);
356 if (createdParticles.Count() != partCounter)
358 if (gPM.IsFinishedAllocating())
360 ErrorEx(
string.Format(
"Not enough particles in pool for EffectArea: %1",
m_Name));
361 OnParticleAllocation(gPM, createdParticles);
365 gPM.GetEvents().Event_OnAllocation.Insert(OnParticleAllocation);
370 OnParticleAllocation(gPM, createdParticles);
380 if (p.GetOwner() ==
this)
381 m_ToxicClouds.Insert(p);
385 int GetRequesterIndex(
string type)
387 typename t = type.ToType();
392 return req.GetRequesterIDX();
401 void CreateTrigger(
vector pos,
int radius )
404 pos[1] = pos[1] - m_NegativeHeight;
410 m_Trigger.SetCollisionCylinder( radius, ( m_NegativeHeight + m_PositiveHeight ) );
416 EffectTrigger.Cast( m_Trigger ).SetLocalEffects( m_AroundParticleID, m_TinyParticleID, m_PPERequesterIdx );
418 m_Trigger.Init(
this, m_EffectsPriority);
427 override void EEDelete(
EntityAI parent )
431 GetGame().ObjectDelete( m_Trigger );
435 if ( (
GetGame().IsClient() || !
GetGame().IsMultiplayer()) && m_ToxicClouds )
437 foreach (
Particle p : m_ToxicClouds )
443 super.EEDelete( parent );
448 player.IncreaseEffectAreaCount();
452 player.DecreaseEffectAreaCount();