Maturity: Draft. How mods add quests, phone conversations, objectives, map pins, scenes and long-lived systems to Cyberpunk 2077 without replacing the game's own quests; how script and quest graphs talk through facts; how braindances are built; what can be generated at run time; and what can be reloaded live. Consolidated on 29 September 2026 from six installed story mods (the B1 deep dive), their quest, scene and journal resources serialised with WolvenKit CLI 9.0.1 into a private scratch folder, the decompiled 2.31 script bundle (redscript-cli 0.5.31), and the source of ArchiveXL, Red Hot Tools and RED4ext.SDK. Nothing here has been seen in a game session. Grades follow the knowledge rules; resource includes a mod resource read as serialised JSON.
This page answers: what is a mod quest made of, how do the parts connect, how could XF Studio author, generate and live-test one, and how are braindances and persistent world systems built?
Sources
| Source | Version studied | Used for |
|---|---|---|
| Game scripts (decompiled bundle) | 2.31 | QuestsSystem facts, JournalManager, TimeSystem listeners, BraindanceSystem, messenger controllers |
Game TweakDB source (REDmod tools/) | 2.31 | timeSystem.settings.realTimeMultiplier |
| Dark Future (Nexus 16300), by DarkFortuneTeller | installed 2.0.3; GitHub metadata at a14f03c | System architecture, fact channel, scenes played from script, phone therapist |
| Eviction Notice (23187) | installed 1.0.3 | A complete data-authored quest, request and response facts, remote device state |
| Lizzie's Braindances (11077), by ArmanIII per its script headers | installed 2.31.0.0 | Staged braindance scenes, runtime casting |
Stock Market and News System (6319), by keanuWheeze per its init.lua | installed 1.4.0 | Generated news, journal-free phone contact, quest-completion observer |
| Virtual Atelier Delivery (21482), by DJ_Kovrik | installed 1.0.10 | Game-time clocks, drop-point pins (terminals §6.1) |
| NightlyNow Core (28966), by NightlyNow | installed 1.1.3 | Journal-free phone contact framework in redscript, HUD interaction prompts |
| ArchiveXL | 5474e34 | Quest-phase injection, journal merging, map pins, reload |
| Red Hot Tools | b4d3415 | Hot reload of archives, scripts and tweaks |
| RED4ext.SDK | ad727771 | Braindance quest and scene types |
Installed-mod citations give paths inside each mod's folder in the mod manager. Who made each mod and what it taught us is in the community credits.
1. The short answers
| Question | Answer | Grade |
|---|---|---|
| How does a mod add a quest without replacing one? | It ships a .questphase and lists it under quest: phases: in an ArchiveXL .xl with a parent quest (base\); ArchiveXL wires it to the parent's start node and starts it once per save (§2.1). | source |
| Where do objectives, messages and pins live? | In the mod's .journal, merged by ArchiveXL's journal:; quest graph nodes change each entry's state (§2.3). | source resource |
| How do script and quest graph talk? | Through facts: named integers in the save. Graphs wait on and set them; script reads, writes and listens (§2.4, §4). | source resource |
| How are map pins placed? | A gameJournalQuestMapPin under an objective points at a node ref, usually a marker the mod placed in its own sector; ArchiveXL makes the pin (§2.5). | source resource |
| Can script create phone messages? | Not journal entries. It can activate pre-authored ones, rewrite or fill their text as they are drawn, or inject a journal-free contact into the phone's lists (§2.6). | source |
| Are braindances data? | Vanilla braindances are scenes played in braindance mode with clue nodes; the one braindance mod installed stages ordinary scenes and casts them at run time (§5). | source resource |
| Can a quest be generated? | No installed mod does; graphs are fixed data parametrised by facts and TweakDB flats (§6). | resource |
| Can quest content be reloaded live? | The journal, scenes (on their next start), scripts and tweaks can; a phase that is already running cannot (§7). | source; phases hypothesis |
2. The parts of a mod quest
2.1 Attaching a phase
- Declaration.
quest: phases:takespath(the mod phase) andparent(a.questor.questphase), and optionallyinput/connectionandoutputas a node-id path plus socket, andinterceptto cut an existing link source ArchiveXLQuestPhase/.Config.cpp:10-60 - Default wiring. With no
input, the phase node is connected from the parent graph's start node (Out→In1) sourceQuestPhase/. WithExtension.cpp:178-238, 240-275 output, bothOutandOut1of the mod phase connect to the named node'sIn(orIn1for a phase node) source same. - Started once per save. For phases merged into a
.quest, ArchiveXL sets a fact keyed by the new node's path when a quest starts and, when a save is restored, force-starts the node (socketIn1) if that fact is unset, then sets it. So a mod added mid-playthrough starts on the next load, and never twice sourceExtension.cpp:97-176. - Node ids are CRC-16. The injected node's id is a 16-bit CRC of
"<phase path>:<parent node id>"; if a node with that id already exists in the parent graph, the phase is skipped with a log warning sourceExtension.cpp:354-392. Collisions are rare but possible as more phases target the same quest hypothesis. - New Game+ in one line. An ArchiveXL resource scope (
resource: scope: df_) used as thecombined_ scope.quest: [cyberpunk2077.quest, mod\ quest\ newgameplus.quest, …] parentexpands to every listed quest resource Dark Future and Eviction Notice.xl; sourceExtension.cpp:35-78(ExpandList). Phantom Liberty's standalone start needsep1\as well resource Lizzie's Braindancesquest\ ep1_ standalone.quest .xl. - Sub-phases. A root phase starts further mod phases with
questPhaseNodeDefinition(phaseResource), entered through namedquestInputNodeDefinitionsockets (SystemStart,DeliveryStart) and left throughquestOutputNodeDefinition(Terminating). Only root phases need listing in the.xlresource Eviction Notice (30 phases, 21 listed).
2.2 Node vocabulary seen in mod phases
Node ($type) | Used for | Seen in |
|---|---|---|
questInputNodeDefinition / questOutputNodeDefinition | Named entry and exit sockets | all |
questPauseConditionNodeDefinition | Wait until a condition holds: questFactsDBCondition (questVarComparison_ with comparisonType, factName, value; questVarVsVarComparison_ comparing two facts), questJournalCondition (questJournalEntryState_, e.g. a phone choice Succeeded), questTriggerCondition (player IsInside/IsOutside a trigger area node ref), questTimeCondition (questRealtimeDelay_, questGameTimeDelay_), questUICondition (questMenuState_ Closed), questLogicalCondition (and/or of these) | DF, EN |
questConditionNodeDefinition | Branch True/False | EN |
questSwitchNodeDefinition | First_ cases on fact values | DF, EN |
questFactsDBManagerNodeDefinition (questSetVar_) | Set a fact (setExactValue) or add to it (no setExactValue) | DF, EN |
questJournalNodeDefinition (questJournalQuestEntry_) | Set an entry Active, Succeeded, Failed, Inactive; sendNotification, trackQuest | DF, EN |
questSceneNodeDefinition | Play a .scene at a marker (scnWorldMarker node ref, #player for V), entering by entry-point socket, leaving by exit sockets | DF, EN, LBD |
questPhaseNodeDefinition | Run a nested phase | EN, LBD |
questCutControlNodeDefinition | Stop the sibling branches (the other replies) | DF, EN |
questLogicalHubNodeDefinition | Join several inputs | EN |
questItemManagerNodeDefinition (questAddRemoveItem_) | Give or take items (AddItem, RemoveByItemID) | EN |
questWorldDataManagerNodeDefinition (questShowWorldNode_) | Show a hidden node | EN |
questInteractiveObjectManagerNodeDefinition (questDeviceManager_) | Device actions on a node ref (ForceON, ForceOFF, QuestStartGlitch) | EN |
questUIManagerNodeDefinition | Push or pop a UI context (CinematicCamera); show a journal onscreen popup (questTutorial_ / questShowPopup_) | DF, EN |
questGameManagerNodeDefinition (questGameplayRestrictions_) | Add or remove restrictions (NoWorldInteractions, NoTimeSkip, NoPhone, BlockDeviceInteractions …) around a scene | DF |
questAudioNodeDefinition, questVoicesetManagerNodeDefinition | UI sounds; a voiceset line from V | EN |
resource the serialised phases of Dark Future, Eviction Notice and Lizzie's Braindances.
2.3 The journal
| Path shape | Class | Holds |
|---|---|---|
contacts/ | gameJournalContact | Name key, type (Texter), avatarID (a TweakDB PhoneAvatars record), useFlatMessageLayout, isCallableDefault |
contacts/ | gameJournalPhoneConversation | Title key |
…/ | gameJournalPhoneMessage | Text key, sender (NPC or player), delay in seconds, optional image and attachment |
…/ | gameJournalPhoneChoiceGroup / gameJournalPhoneChoiceEntry | The player's replies; a choice becomes Succeeded when picked |
quests/ | gameJournalQuest (type: MinorQuest) with gameJournalQuestDescription and a gameJournalQuestPhase of gameJournalQuestObjectives | Title, description, objective texts |
…/ | gameJournalQuestMapPin | Map pin (§2.5) |
…/ | gameJournalQuestCodexLink | Links an objective to a phone choice group ("text Avery") |
onscreens/ | gameJournalOnscreen | Popup title and description |
codex/ | gameJournalCodexEntry + gameJournalCodexDescription | Codex pages; script turns them on with JournalManager.ChangeEntryState |
resource darkfuture.journal, eviction_; source Dark Future Main/ (UpdateCodexEntries).
- Text keys. Journal text fields hold plain string keys (
DarkFutureTextMsg_); ArchiveXL converts each to… LocKey#<FNV1a64 of the key>when it merges the journal, and the mod'slocalization: onscreens:JSON supplies the strings under the same keys source ArchiveXLJournal/.Extension.cpp:478-501 - Script can read and change entry states, not create entries (
JournalManageroffers reads andChangeEntryState; the entry classes areimportonly) source (terminals §3.3).
2.4 Facts
- What they are. Named 32-bit integers in the save's
FactsDB, keyed by the FNV-1a 32-bit hash of the name source ArchiveXLsrc/; source save layout in save files. A fact never set reads 0.Red/ QuestsSystem.hpp:69-94 - Script API.
QuestsSystem.GetFact(n"name"),SetFact(n"name", value),RegisterListener(n"name", object, n"callback")→ id,UnregisterListener(name, id); CET usesGetFactStr/SetFactStrsource Dark FutureUtils/; Stock MarketDFFactListenerUtils.reds questManager.lua. - Facts are the story's public interface. Mods read vanilla quest facts to react to the story: prologue done (
q001_,01_ go_ to_ sleep_ done q101_), Phantom Liberty start (enable_ activities_ flat q301_), point of no return (00_ done q115_), apartments owned (point_ of_ no_ return dlc6_), story choices (apart_ *_ purchased sq021_,randy_ saved sq028_,kerry_ relationship sq030_,romance q305_), Dogtown open (medal_ given_ away q302_),done wanted_source Dark Futurelevel Services/,DFGameStateService.reds Conditions/; NightlyNowDFConditionSystemHumanityLoss.reds:508-528 Utils/; resource Eviction NoticeQuest.reds new_.game_ experience.questphase - Facts are also an inter-mod bus. Idle Anywhere, Immersive Food Vendors and Immersive Bartenders publish what V consumed as
dec_fact values (dark_ * -1ready,≥ 0an item index), and Dark Future listens sourceGameplay/.DFModCompatSystem.reds - Namespacing matters: a fact is a global name; every mod here prefixes its own (
df_,fact_ … en_,fact_ … lizzies_).bds_ …
2.5 Map pins
| Route | How | Evidence |
|---|---|---|
| Journal pin on a mod marker | gameJournalQuestMapPin under an objective: mappinData.mappinType Mappins.QuestStaticMappinDefinition, variant DefaultQuestVariant, visibleThroughWalls, enableGPS, offset, slotName UI_, and reference a node ref to a static marker in the mod's World Builder sector ($/). ArchiveXL collects the pin at journal load and resolves its position from the node ref, in new sectors too | resource eviction_; source ArchiveXL Journal/ |
| Pin on a dynamic entity | A reference by dynamicEntityUniqueName is left to the engine | source same, CollectMappin |
| A spawned device's own pin | Spawn a DropPoint device; the vanilla drop-point system registers its pin | source Virtual Atelier Delivery VirtualAtelierDelivery.reds:3454-3468 |
The pin shows while its objective is active and the quest is tracked [hypothesis: standard journal behaviour; not checked here].
2.6 Phone messages and contacts
| Route | Dynamic text? | Needs the journal? | Evidence |
|---|---|---|---|
| Quest graph activates pre-authored messages and choices | No | Yes | resource Dark Future, Eviction Notice |
Script rewrites a pre-authored message's text, then re-activates it with JournalNotifyOption.Notify | Yes, capped by the slots authored | Yes | source Virtual Atelier Delivery (terminals §6.1) |
Wildcards ({EN_) in localised text, replaced in MessangerItemRenderer.SetMessageView and the reply renderer as each item is drawn | Yes, in fixed messages | Yes | source Eviction Notice Gameplay/ |
A journal-free contact: add a ContactData (own hash, MessengerContactType.SingleThread) in MessengerUtils.GetSimpleContactDataArray and JournalManager.GetContactDataArray, answer GetMessageDataArrayForContact for its hash, fill MessengerDialogViewController with messages and replies, and push a HUD toast (JournalNotificationQueue.AddNewNotificationData with PhoneMessageNotificationViewData) | Fully | No | source NightlyNow Core Holo/; Stock Market modules/ |
2.7 Scenes
- A scene has named entry points and exit points; a quest scene node exposes them as input and output sockets resource every scene read.
- Actors and props: V as
scnPlayerActorDeffound in context; props asscnPropDefwithentityAcquisitionPlan: spawnDespawn, so a scene can bring its own objects resource Dark Futuredarkfuture_(16 entry points, one per prop).item_ consume_ anim_ drink_ sip_ righthand.scene - Events seen: dialogue lines (
scnDialogLineEvent, V's vanilla lines by string id), cinematic idle changes for V in a car seat (scnChangeIdleAnimEvent), skeletal animation (scnPlaySkAnimEvent), audio, VFX, camera parameters resource Dark Future scenes. - Pickup interactions: a scene with a
show_entry, achoice hide_entry driven by a trigger, and anchoice item_exit makes a world pickup with a choice prompt resource Eviction Noticetaken glen_#23, #26, #34.delivery.questphase - Scenes may contain quest nodes (
scnQuestNodewrapping fact, switch and condition nodes) resource Dark Future scenes. - Voiced mod scenes get lip sync through ArchiveXL
localization: lipmaps:(lip sync §5).
2.8 World pieces
A quest's places are ordinary World Builder sectors in the mod's own streaming block: static markers for scenes and pins, trigger areas, hidden props revealed by questShowWorldNode, and devices registered through a .devices patch; always-loaded sectors hold markers that scenes must find from afar resource Eviction Notice (22 sectors, custom_), Dark Future (worldbuildergroup_). The streaming side is in world and streaming.
3. A minimal quest recipe
The smallest complete quest built only from parts the installed mods prove, in the order a tool would emit them. XF names follow the naming contract (xfs_ identifiers, XF-branded titles).
- Place the world. A World Builder sector in the mod's block: a static marker at the goal, a trigger area around it, optionally a hidden prop. Note their node refs (
$/). resource Eviction Notice.mod/ <sector>/ #<name> - Write the journal (
xfs_, listed under…\ journal\ ….journal journal:):contacts/(xfs_ fixer gameJournalContact,Texter, an avatar record) with a conversation holding an intro message, a choice group with Accept and Decline, and a thanks message;quests/(minor_ quest/ xfs_ job gameJournalQuest,MinorQuest) with a description and one phase holding two objectives: Go to the drop (with agameJournalQuestMapPinon the marker) and Text the fixer (with agameJournalQuestCodexLinkto the reply group). All texts are keys supplied bylocalization: onscreens:JSON. resource source
- Write the phase (
xfs_):…\ quest\ xfs_ job.questphase In1→ pause untilxfs_→ message introjob_ offer > 0 Active(with notification) → choice groupActive→ pause on AcceptSucceeded(and a parallel pause on Decline into a cut-control node) → questActive, objective 1Active→ pause until playerIsInsidethe trigger → (optional) scene with a pickup choice → objective 1Succeeded, add the reward item (questAddRemoveItem_) → objective 2NodeType Active→ reply groupActive→ pause on its choiceSucceeded→ objective 2 and questSucceeded→ setxfs_. resource Eviction Noticejob_ done = 1 glen_delivery.questphase - Attach it:
quest: phases: - path: …\; addxfs_ job.questphase, parent: <a scope covering cyberpunk2077.quest and the New Game+ quests> ep1\for Phantom Liberty starts. sourcequest\ ep1_ standalone.quest - Start it. Either from the graph (a pause on vanilla facts such as
q101_, then a game-time delay) or from script by settingenable_ activities_ flat xfs_. Money rewards and anything computed go through a request fact answered by script (§4). resource sourcejob_ offer = 1 - Package the phase, journal and sectors in one archive, texts in a second (so translators replace only that), and the
.xlbeside them; version the facts, because saves keep them. resource Eviction Notice's split archives.
What this recipe does not yet cover: dialogue with voiced NPCs in the world (scenes with actors and lines), companions, and fail states; those need scene authoring, which the installed mods show only for V and props. Directing an NPC and offering V choices without a scene (runtime AI commands, text lines and a hub added to the game's dialogue widget) is on NPC direction.
4. How script and quest graphs work together
| Pattern | Shape | Evidence |
|---|---|---|
| Command channel | A looping phase: pause until fact > 0 → switch on the value → scene entry point → reset fact = 0 → loop. Script plays scene N by SetFact(fact, N) | resource Dark Future darkfuture_, darkfuture_ |
| Request and response | Graph sets …_ and pauses until it is 0; script's listener computes, writes result facts, resets the request; graph branches on the result | resource Eviction Notice glen_ #105-#106, #113-#115; source ENRentSystemBase.reds:620-660 |
| Readiness gate | Scripts set …_ at start; the root phase waits for all of them before starting sub-phases | resource Eviction Notice new_ #7-#11, #54 |
| Debug trace | Graph writes numbered values to a debug fact; script logs them | resource same, #40-#45 |
| Graph → entity events | A named ActionEvent sent to an entity lands on an @addMethod handler of its class; Lizzie's Braindances receives such events on its performers (which of its graphs sends them was not read) | source Lizzie's Braindances NPCPuppet.reds:57-106; sender hypothesis |
| Game-state gate | Script refuses to start story beats before the prologue ends, after the point of no return, as Johnny (PlayerPuppet.IsReplacer), in cyberspace or fury, and when PlayerStateMachine.SceneTier is above 2 | source Dark Future Services/ |
| Game-time clock | TimeSystem.RegisterListener(entity, event, GameTime, repeat) delivers an event at a game time (vanilla passes -1 to repeat, 1 for once); DelaySystem.DelayCallback(cb, seconds, affectedByTimeDilation) for real-time intervals. Game time runs at timeSystem.settings.realTimeMultiplier (8.0) | source 2.31 gameTimePrereq.script:39-43; Eviction Notice ENPropertyStateService.reds:158-162; resource time.tweak:5 |
5. Braindances
5.1 The vanilla braindance
| Piece | What it is | Evidence |
|---|---|---|
| The recording | A scene played in braindance mode, with conditions on layer (Visual, Audio, Thermal), perspective (first or third person), playback speed, and jump, pause, reset and rewind states | source SDK scn/, BraindancePerspective_, BraindancePlaying_ and siblings |
| Per-performer presentation | Scene events: BraindanceVisibilityEvent (a performer's custom material parameter and first- and third-person render settings), VFXBraindanceEvent (effect and glitch effect, rewindable), UIAnimationBraindanceEvent | source SDK scn/ |
| Clues | Quest nodes AddBraindanceClue_ (clueName, startTime, endTime, layer), DiscoverBraindanceClue_, EnableBraindanceFinish_ | source SDK quest/ |
| Mode and controls | BraindanceSystem (persistent input mask, editor-state, pause and camera-toggle requests, isInBraindance), the player state machine's braindance locomotion (fly, fast fly) and controls | source 2.31 core/, cyberpunk/ |
| UI | The Braindance blackboard (vision mode, progress, section time, clue, IsFPP, playback speed and direction) and BraindanceGameController (timeline, clue markers, layer bar) | source core/, cyberpunk/ |
5.2 Staged braindances (Lizzie's Braindances)
The installed braindance mod plays ordinary scenes in real places and parametrises them:
- The player picks a braindance and a cast in a menu; the menu writes facts for location, loops, music and each performer slot's character, appearance and flags source
MenuUIController.reds:3286-3306. - Casting: six fixed
Character.LizziesBDs_records are rewritten withPerformer* TweakDBManager.SetFlat(entityTemplatePath,appearanceName,genders, names, attitude) andUpdateRecord, so the scene's spawn-by-record actors become the chosen vanilla NPCs, V's cutscene rig or another mod's character sourceMenuUIController.reds:3787-3848. - Dressing: named
ActionEvents (sent, presumably, from its graphs hypothesis) tell each performer to switch appearance (ScheduleAppearanceChange) sourceNPCPuppet.reds:57-150; per-instance parts are set by editing mesh components inNPCPuppet.OnRequestComponentsbefore the entity streams sourceNPCPuppet.reds:162-276. - Content packs register extra characters through a
CustomCharacterLoaderEventhandler sourceClasses.reds:1081-1130.
5.3 What player-made or generated braindances would need
- A recording is a scene resource. Recording V's play as a braindance means writing a
.scene(tracks of positions, animations and camera) from captured data, the same export problem as a quest editor hypothesis. - Casting by record rewrite gives any number of variants of one authored scene [source, above]; a generator would vary cast, place and music through facts and flats.
- Investigation gigs would be a template scene plus generated
AddBraindanceCluenodes over its timeline; whether clue nodes work on a mod scene in braindance mode is untested hypothesis. - Entering braindance mode from a mod has no installed example; the first probe is to replay a vanilla braindance quest's node sequence against a mod scene hypothesis.
6. Persistent systems and generated content
6.1 Where long-lived state lives
| Mechanism | Example | Survives | Evidence |
|---|---|---|---|
persistent fields on a ScriptableSystem (scalars, arrays, nested objects) | Dark Future (39 fields), Virtual Atelier Delivery (34, nested order objects), Lizzie's (arrays of storage objects, with old layouts kept for migration) | The save | source |
@addField persistent on a vanilla device's persistent state | Eviction Notice adds three fields to ApartmentScreenControllerPS | The save, with that device | source Devices/ |
| Facts | Every mod's flags and counters | The save | resource |
Codeware dynamic entities with persistSpawn | Delivery drop points | The save | source |
| A CET per-save file joined by a fact | Stock Market: psiberx's GameSession writes a session key fact (_) and a Lua data file named by save time in the mod folder | The file beside the mod; lost if the file goes | source modules/ |
| Mod Settings | Every settings screen | Mod Settings' own storage, not the save | source |
More on save layout in save files §4.
6.2 A robust architecture (Dark Future)
A base system class with a fixed lifecycle (Init → systems, blackboards, data, listeners, timers → InitSpecific; Suspend, Resume, Stop); start only after RadialWheelController.OnLateInit (safe for status effects), in dependency order, suspend in reverse; a game-state gate before any story beat; Codeware callback-system events for death, time skip and settings; published lifecycle events for add-ons; a tiny save footprint; and an uninstall path (switch off in settings, save, then remove files) source Dark Future System/, Main/; resource upstream README.md. Clocks that pause when they should: Virtual Atelier Delivery stops its order clock during braindances, as Johnny and in the time-skip menu source VirtualAtelierDelivery.reds:566-595.
6.3 What is generated at run time
Random encounters from the district's gang (District_ chain → faction character lists → Codeware DynamicEntitySystem) source Dark Future DFRandomEncounterSystem.reds; news from gameplay observers and from vanilla quest completions (JournalNotificationQueue.OnJournalUpdate, gameJournalQuest Succeeded) source Stock Market questManager.lua:24-48; orders and their messages source Delivery. No installed mod generates quest graphs or journal entries; dynamic content is either fixed data parametrised by facts and flats, or journal-free UI.
7. Hot reload
| Change | Live? | Grade |
|---|---|---|
| Journal in a mod archive | Yes: Red Hot Tools moves archives from archive/ into archive/, reloads them, forgets their resources and calls ArchiveXL's reload, which rebuilds the journal and keeps the tracked quest | source Red Hot Tools Archives/; ArchiveXL Journal/ |
| A scene | On its next start, since the old resource is forgotten | hypothesis |
| A phase that is running | No; merged phases are patched at preload and running instances keep their definitions. Reload the save | [hypothesis from source] ArchiveXL QuestPhase/ |
| Facts | Yes: any script, CET or bridge write | source |
| redscript, TweakDB | Yes (ReloadScripts, ReloadTweaks), except struct fields and new request handlers | source Red Hot Tools README.md |
Under MO2, a hot-reloaded archive lands in MO2's overwrite folder, because the move targets the virtual archive/ source ArchiveLoader.cpp:150-176 [hypothesis for the VFS effect].
8. What this means for XF Studio
- A quest editor is feasible as a writer of
.questphase,.journal, sector and.xlfiles in WolvenKit's JSON form, using only the node types in §2.2; start from the §3 recipe hypothesis. - Live testing through the bridge needs fact read, write and watch, journal entry state, and a remote device event by node ref (the Eviction Notice route:
CreateNodeRef→EntityID.FromHash(NodeRefToHash(…))→CreatePersistentID(id, n"controller")→PersistencySystem.QueuePSEvent) source Eviction NoticeENRentSystemBase.reds:551-555, 756-774; bridge side hypothesis. - Keep quest logic restartable: short phases started by facts can be retested after a hot reload without reloading the save hypothesis.
- An XF phone presence (session notices, a Studio contact) can be built journal-free in our own code, NightlyNow style [source, pattern].
Open questions
- Does ArchiveXL's forced start run for a phase added to a save whose quest has already passed the start node, in every case (Act 2 saves, Phantom Liberty standalone)?
- Does
TimeSystem.RegisterListenerwithrepeat = 0fire once or repeat? (Eviction Notice depends on it.) - Do
AddBraindanceClue_and braindance mode work with a mod scene?NodeType - After a Red Hot Tools reload, does a newly started scene node load the new scene file?
- How often do 16-bit injected phase ids collide across the installed phase mods, and with vanilla node ids in
cyberpunk2077.quest? - Does a quest map pin on a node ref in an unloaded mod sector show at the right place before the sector streams?
Related pages
Terminals and arcade · World and streaming · Save files · Lip sync · Player control · Runtime access · B1 deep dive · In-game possibilities