Jump to content

[Papyrus] WorkshopParentScript.WorkshopObjectBuilt not triggering for all built objects?


sialivi

Recommended Posts

I'm just getting started with Papyrus, and I'm a bit stumped:

My script needs to get a reference to any objects being built in Workshop Mode.
I've registered the script to listen for the custom WorkshopParentScript.WorkshopObjectBuilt event.
Unfortunately, this only seems to trigger for Furniture; building other types of objects doesn't seem to trigger the event.

I'm clearly missing something, so any pointers would be appreciated.

Edit:
I was wrong about the object types.
- Not all Furniture triggers the event; things like beds and guard posts generates the event, but objects like chairs doesn't.
- Some non-Furniture objects triggers it, turrets for example.
 

Link to comment
Share on other sites

I had actually tested removing the WorkshopObjectScript from one of the objects that does trigger the event, and it still did. I must have messed up that test.

If that's the script that triggers the event, and only a subset of the buildable objects have that script attached, I'm not sure how I would detect the rest.

Link to comment
Share on other sites

Custom event OnWorkshopObjectBuilt is sent for any object placed in the Workshop Menu (if WorkshopObjectScript is attached to them; see the event sender function "BuildObjectPUBLIC" in WorkshopParentScript).

; Register
Event OnQuestInit()
	Quest WorkshopParent = Game.GetFormFromFile(0x0002058E, "Fallout4.esm") as Quest
	RegisterForCustomEvent(WorkshopParent as WorkshopParentScript, "WorkshopObjectBuilt")
EndEvent

; Receive
Event WorkshopParentScript.WorkshopObjectBuilt(WorkshopParentScript akSender, var[] arguments)

	; kargs[0] = newWorkshopObject
	; kargs[1] = workshopRef

	; Variables
	ObjectReference newWorkshopObject = arguments[0] as ObjectReference
	ObjectReference workshopRef = arguments[1] as ObjectReference

	; ...

EndEvent

For items spawned by mods (e.g. with PlaceAtMe()) then get linked to the workshop workbench reference ("workshopRef"), this event is not sent. For them, you can use OnLoad() with if statements, to determine they got 3D loaded because they were just built and not because the player entered the area, UI.IsMenuOpen("WorkshopMenu"), used along with a PlayerRef.GetDistance(newWorkshopObject) < {MaxReasonableObjectBuildDistance}. If you'd like to avoid F4SE depenency, you can store the IsMenuOpen state of WorkshopMenu with OnMenuOpenCloseEvent in a script variable for example.

Notes:

   - the workshop system is considerably complex, it may be a bit overwhelming if you're new to Papyrus

   - test your script in vanilla environment (vanilla workshop scripts, no mods enabled, etc.) in case the "WorkshopObjectBuilt doesn't being sent for all workshop objects" issue is caused by a mod

Edited by LarannKiar
  • Thanks 1
Link to comment
Share on other sites

All the pointers are greatly appreciated.

I am using a "cleanroom" setup for working on the mod, and the code snippet matches what I'm doing, so I'm glad that's confirmed as valid.

Wouldn't using OnLoad like that mean I would need to attach a script to every buildable object, including those added by other mods?
And those events would fire absolutely everywhere in the world as you play, before reaching the if-statement?
If so, it sounds quite... heavy.

 

 

Link to comment
Share on other sites

13 hours ago, sialivi said:

All the pointers are greatly appreciated.

I am using a "cleanroom" setup for working on the mod, and the code snippet matches what I'm doing, so I'm glad that's confirmed as valid.

Wouldn't using OnLoad like that mean I would need to attach a script to every buildable object, including those added by other mods?
And those events would fire absolutely everywhere in the world as you play, before reaching the if-statement?
If so, it sounds quite... heavy.

 

 

OnLoad can be used for objects you have foll control over, like custom workshop objects you made. And yes, you'd need to attach a script to these objects.

Take a look at the vanilla workshop scripts, they rely on OnLoad as well. If you know what objects a script with OnLoad is attached to and what to expect, they won't cause heavy script load.

(OnLoad was meant for scenarios like items requiring special handling for mod compatibility and such).

Since WorkshopObjectScript is already attached to buildable objects as well, for a "catch all" event WorkshopObjectBuilt is preferred.

Edited by LarannKiar
Link to comment
Share on other sites

Looking over WorkshopObjectScript I'm not immediately seeing anything that would prevent it from being used on all buildable objects, but maybe there is.

Either way, I would essentially need a way to iterate over all buildable objects to attach a script since doing it via plugin overrides isn't feasible due to the number of mods that add new buildable objects.

I just remembered Workshop Plus is supposed to have some kind of undo feature. I wonder how they've tackled this, or if that feature also only works with objects that have the WorkshopObjectScript attached.

Link to comment
Share on other sites

Can confirm what LarannKiar said about the WorkshopObjectBuilt event. I will add that it might not work properly if the cell you build in is not tagged for workshop location.

Re WS+:

WS+ keeps objectreference arrays around for the undo, forcing things to become persistent.
Imho, the feature creates way more problems than it solves. For example, Actor Values on an object are lost after store/undo - The code to recover them AVs simply does not work.
This means that an object that was removed from the game world and then placed back via UNDO will often not work properly.
If you must absolutely, positively use it, set the UNDO feature to exclude powered objects at least, as forcing persistency on powered objects has many unintended side effects.
As such,  the UNDO feature is probably the reason for a whole bunch of very weird bug reports.

There is another feature "Keep Workshop Objects Persistent" or whatever, which will also force persistency, even on powered objects. Turn this feature OFF unless you play on console.

Link to comment
Share on other sites

  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...