RegisterForUpdate - Form
Registers this active magic effect/alias/form for periodic update events. The interval is only counted when the game is not in menu mode. For example, you register for update every 5 seconds. 2 seconds go by and the player opens the menu for 10 seconds. Once the player puts the menu away, 3 more seconds will go by before your next update comes in. Only the specific form, alias, or magic effect that registered will get the event - it will not be relayed to attached aliases or magic effects.
Function RegisterForUpdate(float afInterval) native
- afInterval: How often, in seconds, the update event should be sent
A value smaller than the amount of time it takes your code to complete plus a little overhead time can cause the game to freeze as the scripting system becomes overwhelmed. For any value less than a few seconds RegisterForSingleUpdate is much safer.
; Register to receive update events every 10 real-time seconds RegisterForUpdate(10.0)
- Aliases and quests will automatically unregister for this event when the quest stops. Active magic effects will automatically unregister when they are removed.
- Subsequent calls to RegisterForUpdate will override previous ones - i.e. calling it back to back will result in updates at the second call's interval, but not the first. It does not interfere with updates registered via RegisterForSingleUpdate.
Using this function should be done with great care and RegisterForSingleUpdate should be preferred in almost every circumstance.
Indeed, RegisterForUpdate comes with a few problems:
- If a mod is removed, its OnUpdate handler will still be registered and the game engine will continue to try to invoke it. This will result in periodic errors on every tick because of the game reporting that the handler no longer exists. If you initially registered a small update interval, this can harm performances significantly.
- Even if your mod still exists, you may not exclude the possibility that a bug manifests itself and causes periodic errors. A better behavior if your event handler contains a bug would be to cancel the automatic updates, which is achieved through RegisterForSingleUpdate.
- This also complicates development since simply modifying the OnUpdate handler has no effect: as long as the old handler was registered, it will continue to be used unless you explicitly unregister for updates, then register again. This will also output periodic error messages because of the game reporting that the executed version is different from the current one.
- Last but not least, OnUpdate is a very frequent cause of savegames bloat and general bugs, forcing the user to abandon their current game and restart a new one. This occurs when the OnUpdate handler takes more time to run than the update interval it was registered with. The result is that new calls are queued faster than they are processed, preventing other scripts to run, consuming increasing memory and can lead to savegames as large as one gigabyte! Unfortunately, since almost every call to a native function suspends a function's execution for one whole frame, the phenomenon is bound to happen if the handler contains more native calls than the number of frames between each handler's call.
Also note that other events do not have those problems. This is specific to RegisterForUpdate.
Anyway, all of those problems are avoided by using RegisterForSingleUpdate instead:
- If the script is missing or contains an error, it will never be called again.
- If you modify OnUpdate and reload your game, the old version will be only called once. After that the new version will be the one called.
- The next call can never happen before the previous one completed.
OnUpdate can still be used in the following circumstances:
- The script is attached to something that is guaranteed to not stick around for long (for instance, a short duration magic effect). It is unlikely that a player will uninstall the mod in the middle of a fight that features mod content.
- When timing is critical. Due to script processing time, a chain of single updates takes an unpredictable and significant amount of additional time to execute. In cases where milliseconds matter (eg. when using continuous havok pushes to levitate objects or ragdolls), single updates may be unworkable. Again, make sure the script does not stick around for long. Remember that Delete() only actually deletes an object when the cell is unloaded!
function SomeInitializationFunction() RegisterForSingleUpdate(0.5) ; OnUpdate will be called once. endfunction Event OnUpdate() ; Do some stuff RegisterForSingleUpdate(0.5) ; OnUpdate will be called one more time. endEvent
It may also be wise to override the handler for OnPlayerLoadGame. That way, if OnUpdate previously contained an error and is no longer fired as a result, it will resume once the game is reloaded, hopefully with a modified version that fixes the problem. Note that this event is only fired on the player actor, on the ActiveMagicEffects put on the player and on the ReferenceAliases that reference the player.
Event OnPlayerLoadGame() RegisterForSingleUpdate(0.5) EndEvent