Arma Reforger Explorer 1.7.0.54
Arma Reforger Code Explorer by Zeroy - Thanks to MisterOutofTime
Loading...
Searching...
No Matches
SCR_RespawnTimerComponent.c
Go to the documentation of this file.
1[ComponentEditorProps(category: "GameScripted/GameMode/Components", description: "Handles respawn timers for players.")]
5
6#define RESPAWN_TIMER_COMPONENT_DEBUG
7
10{
11 [Attribute("10", UIWidgets.EditBox, "Default time in seconds that a player has to wait after dead to respawn.", category: "Respawn Timers")]
12 protected float m_fRespawnTime;
13
18
20 protected RplComponent m_RplComponent;
21
22 #ifdef RESPAWN_TIMER_COMPONENT_DEBUG
23 protected static bool s_DebugRegistered = false;
24 #endif
25
26 //------------------------------------------------------------------------------------------------
30 override bool RplSave(ScriptBitWriter writer)
31 {
32 writer.WriteFloat(m_fRespawnTime);
33 writer.WriteInt(m_mRespawnTimers.Count());
34 foreach (int playerId, SCR_RespawnTimer timer : m_mRespawnTimers)
35 {
36 writer.WriteInt(playerId);
37 timer.RplSave(writer);
38 }
39
40 return true;
41 }
42
43 //------------------------------------------------------------------------------------------------
47 override bool RplLoad(ScriptBitReader reader)
48 {
49 reader.ReadFloat(m_fRespawnTime);
50
51 int count;
52 reader.ReadInt(count);
53
54 for (int i = 0; i < count; i++)
55 {
56 int playerId;
57 reader.ReadInt(playerId);
58
59 // Create new instance
60 if (!m_mRespawnTimers.Contains(playerId))
61 m_mRespawnTimers.Insert(playerId, new SCR_RespawnTimer());
62
63 // Load instance data
64 m_mRespawnTimers[playerId].RplLoad(reader);
65 }
66
67 return true;
68 }
69
70 //------------------------------------------------------------------------------------------------
72 protected bool IsMaster()
73 {
74 return (!m_RplComponent || m_RplComponent.IsMaster());
75 }
76
77 //------------------------------------------------------------------------------------------------
80 {
81 ChimeraWorld world = GetGame().GetWorld();
82 if (!world)
83 return null;
84
85 return world.GetServerTimestamp();
86 }
87
88 //------------------------------------------------------------------------------------------------
91 void SetRespawnTime(int playerID, float respawnTime)
92 {
93 // Server only
94 if (!IsMaster())
95 return;
96
97 // Set duration and replicate to all clients
98 RpcDo_SetDuration_BC(playerID, respawnTime);
99 Rpc(RpcDo_SetDuration_BC, playerID, respawnTime);
100 }
101
102 //------------------------------------------------------------------------------------------------
105 bool IsPlayerEnqueued(int playerID)
106 {
107 return m_mRespawnTimers.Contains(playerID);
108 }
109
110 //------------------------------------------------------------------------------------------------
115 bool GetCanPlayerSpawn(int playerID, float additionalTime = 0)
116 {
117 if (!IsPlayerEnqueued(playerID))
118 {
119 Print("Provided playerId: (" + playerID + ") in SCR_RespawnTimerComponent was invalid!", LogLevel.ERROR);
120 return false;
121 }
122
123 return m_mRespawnTimers[playerID].IsFinished(GetCurrentTime(), additionalTime);
124 }
125
126 //------------------------------------------------------------------------------------------------
130 int GetPlayerRemainingTime(int playerID, float additionalTime = 0)
131 {
132 if (!m_mRespawnTimers.Contains(playerID))
133 {
134 Print("Provided playerId: (" + playerID + ") in SCR_RespawnTimerComponent was invalid!", LogLevel.ERROR);
135 return false;
136 }
137
138 float remainingTime = m_mRespawnTimers[playerID].GetRemainingTime(GetCurrentTime(), additionalTime);
139 return Math.Ceil(remainingTime);
140 }
141
142 //------------------------------------------------------------------------------------------------
148 override void OnPlayerKilled(notnull SCR_InstigatorContextData instigatorContextData)
149 {
150 super.OnPlayerKilled(instigatorContextData);
151
152 int playerId = instigatorContextData.GetVictimPlayerID();
153
154 // Invalid playerID
155 if (playerId <= 0)
156 return;
157
158 if (instigatorContextData.GetVictimEntity().IsDeleted()) //todo(@langepau): remove hack after character event flow rework
159 return;
160
161 // TODO@AS: Propagate change to owner
162 WorldTimestamp rplTime = GetCurrentTime();
163
164 // Notify all clients, fire locally
165 RpcDo_StartTimer_BC(playerId, rplTime);
166 Rpc(RpcDo_StartTimer_BC, playerId, rplTime);
167 }
168
169 //------------------------------------------------------------------------------------------------
170 override void OnPlayerDeleted(int playerId, IEntity player)
171 {
172 OnPlayerKilled(new SCR_InstigatorContextData(playerId, player, null, Instigator.CreateInstigator(null), true));
173 }
174
175 //------------------------------------------------------------------------------------------------
179 [RplRpc(RplChannel.Reliable, RplRcver.Broadcast)]
180 private void RpcDo_StartTimer_BC(int playerId, WorldTimestamp rplTime)
181 {
182 m_mRespawnTimers[playerId].Start(rplTime);
183 }
184
185 //------------------------------------------------------------------------------------------------
189 [RplRpc(RplChannel.Reliable, RplRcver.Broadcast)]
190 private void RpcDo_SetDuration_BC(int playerId, float duration)
191 {
192 m_mRespawnTimers[playerId].SetDuration(duration);
193 }
194
195 //------------------------------------------------------------------------------------------------
198 [RplRpc(RplChannel.Reliable, RplRcver.Broadcast)]
199 private void RpcDo_SetDurationAll_BC(float duration)
200 {
201 foreach (SCR_RespawnTimer timer : m_mRespawnTimers)
202 {
203 timer.SetDuration(duration);
204 }
205 }
206
207 //------------------------------------------------------------------------------------------------
209 override void OnPlayerRegistered(int playerId)
210 {
211 super.OnPlayerRegistered(playerId);
212
213 // Prepare timer
214 SCR_RespawnTimer respawnTimer = new SCR_RespawnTimer();
215
216 // For first spawn to be already finished even when time == 0
217 respawnTimer.SetDuration(m_fRespawnTime);
218 WorldTimestamp startTime;
219 startTime = startTime.PlusSeconds(-m_fRespawnTime);
220 respawnTimer.Start(startTime);
221
222 if (!m_mRespawnTimers.Contains(playerId))
223 m_mRespawnTimers.Insert(playerId, respawnTimer);
224 }
225
226 //------------------------------------------------------------------------------------------------
228 // TODO: Editor team would like to set respawn time for Factions specific
229 void SetRespawnTime(float respawnTime)
230 {
231 // Set default respawn time value
232 m_fRespawnTime = respawnTime;
233
234 // Propagate changes to existing timers for both self and all clients
235 RpcDo_SetDurationAll_BC(respawnTime);
236 Rpc(RpcDo_SetDurationAll_BC, respawnTime);
237 }
238
239 //------------------------------------------------------------------------------------------------
241 float GetRespawnTime()
242 {
243 return m_fRespawnTime;
244 }
245
246// //------------------------------------------------------------------------------------------------
247// override void OnPlayerDisconnected(int playerId, KickCauseCode cause, int timeout)
248// {
249// super.OnPlayerDisconnected(playerId, cause, timeout);
250//
251// // Do nothing for now,
252// // TODO@AS: If needed, remove unused respawn timers?
253// }
254
255 #ifdef RESPAWN_TIMER_COMPONENT_DEBUG
256 protected void DrawDebugInfo()
257 {
258 ArmaReforgerScripted game = GetGame();
259 // Prepare strings to display
260 const string header = "[PlayerID] [PlayerName] [Timer] [IsFinished] [TimerObject]";
261 const string tableFmt = "%1 | %2 | %3 | %4 | %5";
262
263 // Find local pyl
264 int localId = -1;
265 PlayerController playerController = game.GetPlayerController();
266 if (playerController)
267 localId = playerController.GetPlayerId();
268
269 DbgUI.Begin("Respawn Timer Component Diag");
270 DbgUI.Text("RplTime: " + GetCurrentTime());
271 DbgUI.Spacer(10);
272 DbgUI.Text(header);
273
274 WorldTimestamp timeNow = GetCurrentTime();
275 PlayerManager playerManager = GetGame().GetPlayerManager();
276 foreach (int playerId, SCR_RespawnTimer timer : m_mRespawnTimers)
277 {
278 string isFinished = "False";
279 if (timer.IsFinished(timeNow))
280 isFinished = "True";
281
282 string playerIdentifier = playerId.ToString();
283 string playerName = SCR_PlayerNamesFilterCache.GetInstance().GetPlayerDisplayName(playerId);
284 string time = timer.GetRemainingTime(timeNow).ToString();
285 string obj = timer.ToString();
286
287 // if (playerId == localId)
288 string text = string.Format(tableFmt, playerIdentifier, playerName, time, isFinished, obj);
289 if (playerId == localId)
290 text = " > " + text;
291
292 DbgUI.Text(text);
293 DbgUI.Spacer(4);
294 }
295
296 DbgUI.End();
297 }
298 #endif
299
300 //------------------------------------------------------------------------------------------------
301 override void EOnDiag(IEntity owner, float timeSlice)
302 {
303 super.EOnDiag(owner, timeSlice);
304
305 #ifdef RESPAWN_TIMER_COMPONENT_DEBUG
306 if (DiagMenu.GetBool(SCR_DebugMenuID.DEBUGUI_RESPAWN_TIMER_COMPONENT))
307 {
309 }
310 #endif
311 }
312
313 //------------------------------------------------------------------------------------------------
314 override void OnPostInit(IEntity owner)
315 {
316 super.OnPostInit(owner);
317 ConnectToDiagSystem(owner);
318
319 m_RplComponent = RplComponent.Cast(owner.FindComponent(RplComponent));
320 }
321
322 //------------------------------------------------------------------------------------------------
323 override void OnDelete(IEntity owner)
324 {
325 DisconnectFromDiagSystem(owner);
326
327 super.OnDelete(owner);
328 }
329
330 //------------------------------------------------------------------------------------------------
331 // constructor
336 {
337 #ifdef RESPAWN_TIMER_COMPONENT_DEBUG
338 if (!s_DebugRegistered)
339 {
340 DiagMenu.RegisterBool(SCR_DebugMenuID.DEBUGUI_RESPAWN_TIMER_COMPONENT, "", "Respawn Timer", "GameMode");
341 s_DebugRegistered = true;
342 }
343 #endif
344 }
345
346 //------------------------------------------------------------------------------------------------
347 // destructor
349 {
350 #ifdef RESPAWN_TIMER_COMPONENT_DEBUG
351 if (s_DebugRegistered)
352 {
353 DiagMenu.Unregister(SCR_DebugMenuID.DEBUGUI_RESPAWN_TIMER_COMPONENT );
354 s_DebugRegistered = false;
355 }
356 #endif
357 }
358}
ref DSGameConfig game
Definition DSConfig.c:81
SCR_DebugMenuID
This enum contains all IDs for DiagMenu entries added in script.
Definition DebugMenuID.c:4
ArmaReforgerScripted GetGame()
Definition game.c:1398
override bool RplLoad(ScriptBitReader reader)
enum EAIGroupCombatMode ComponentEditorProps(category:"GameScripted/AI", description:"Component for utility AI system for groups")
void SCR_BaseGameModeComponent(IEntityComponentSource src, IEntity ent, IEntity parent)
override bool RplSave(ScriptBitWriter writer)
RplComponent m_RplComponent
void OnPlayerKilled(notnull SCR_InstigatorContextData instigatorContextData)
void OnPlayerDeleted(int playerId, IEntity player)
ref map< int, ref SCR_RespawnTimer > m_mRespawnTimers
void SetRespawnTime(int playerID, float respawnTime)
WorldTimestamp GetCurrentTime()
void SCR_RespawnTimerComponent(IEntityComponentSource src, IEntity ent, IEntity parent)
void DrawDebugInfo()
bool GetCanPlayerSpawn(int playerID, float additionalTime=0)
void ~SCR_RespawnTimerComponent()
int GetPlayerRemainingTime(int playerID, float additionalTime=0)
bool IsPlayerEnqueued(int playerID)
Definition DbgUI.c:66
Diagnostic and developer menu system.
Definition DiagMenu.c:18
proto external Managed FindComponent(typename typeName)
Definition Math.c:13
void Start(WorldTimestamp timeNow)
void SetDuration(float duration)
Definition Types.c:486
override void EOnDiag(IEntity owner, float timeSlice)
proto void Print(void var, LogLevel level=LogLevel.NORMAL)
Prints content of variable to console/log.
LogLevel
Enum with severity of the logging message.
Definition LogLevel.c:14
SCR_FieldOfViewSettings Attribute
override void OnPlayerRegistered(int playerId)
void RplRpc(RplChannel channel, RplRcver rcver, RplCondition condition=RplCondition.None, string customConditionName="")
Definition EnNetwork.c:95
RplRcver
Definition RplRcver.c:59
RplChannel
Communication channel. Reliable is guaranteed to be delivered. Unreliable not.
Definition RplChannel.c:14