Quest audit (docs/quest-audit.md, tools/questscript.mjs), fixes 2-8. New mods/questscript.cpp scans the script code once (giver, own variables, needed NPCs, QIS_OnEnter creations, story-ending failure labels). questfail: generic, giverless, story-ending and NPC-gone failures stay final; a restart restores the variables snapshot taken at Quest_Trigger, deletes OnEnter leftovers, respawns the giver and needed NPCs and gives the accept dialog back. questgiver slimmed on top of questscript. Not yet tested in game. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
31 KiB
Quest audit: how quests fail or get stuck (2026-10-30)
Request (2026-10-26, started 2026-10-30): "iterate through all quests in the
game, and check their conditions for potential failing or stuck up points
given the current implementation and our attempted reset". Done one quest at
a time from the compiled scripts with tools/questscript.mjs (full dump:
<dir> <id>; compact: <dir> --facts <id>).
Scripts: Ancaria per hero class bin\TYPE_NPC_<class>\ (the game writes the
one in use to bin\sgf.bin; this audit reads TYPE_NPC_GLADIATOR, the class
variants differ in a few class quests), Underworld bin\Addon\NetScriptCamp\.
Ancaria: 603 quests in the table (87 + 13 side quests, ~37 main quests, 352
generic DQ_ quests from 16 templates, multiplayer / unnamed sets);
Underworld: 190.
What our mods do (the "reset")
- M1 failure restart (
questfail.cpp,Quest_Endhook): afterLoseQuestran the quest's failure script (QIS_OnLose<id>), the flags go back to available (1), the book entry stays failed with its compass on the giver. Quest variables and NPC states are left as they are. - M2 giver death (
questgiver.cpp): a label of a running quest run for its dead giver (the giver: the NPC spawned with a dialog that has the accept button) is skipped, unless the giver is hostile to the hero (2026-10-30); the quest restarts (M1 plus the variables only this quest writes: 0, the one named after the quest: 1) and the giver's spawn instruction runs again once the body is gone. - M3 load repair (
questgiver.cpp): a running quest whose giver is not alive after loading gets M2, unless the quest morphs its giver. - M4 followers (
followers.cpp): escorts back on the hero's follower list after loading; followers more than 40 cells away are teleported to the hero.
General findings
- G1 M1 keeps the quest variables. Givers' dialogs choose their branch by
bits of the quest variable (
IF 49(bit, "<id>")); bits set while the quest ran stay set after a failure, so the giver shows a "still running" branch without the accept button and the quest can never be taken again. Example 702: the girl's death runslose702; variable 702 keeps bit 1, the giver answers "Qoffen01" withok702. Fix: M1 resets the quest's own variables like M2. - G2 generic quests (2600..3599) are the game's random quest pool;
Quest_Endalready copies them under a new id. M1 should leave them (and their runtime copies) to the game. - G3 one-time world progress. Many targets are spawned once by the start
script or
Region<N>Init, not by the quest. When M2/M3 reset the quest's variables after such a target died, the progress is lost and the target never comes back: stuck. Either keep the variables on M2/M3 or respawn the quest's one-time NPCs (see G6). - G4 duplicates on re-accept.
QIS_OnEntercreates the quest's NPCs and objects again; after a failure the old ones may still be alive. - G5 givers deleted by the script (
DelNPCon the giver): M3 restarts a quest whose giver is gone on purpose. - G6 restart without the NPCs. The restart is pointless when the NPCs the quest needs are one-time spawns and dead or deleted. Idea: respawn them from their spawn instructions like the giver.
- G7 quests without a giver (trigger areas): M1 "restarts" them and erases the failed book entry.
- G8 givers turned hostile by
SetNPCState ... 08 12instead ofMorphare not ing_giverTurns; M3 restarts those quests wrongly, M1 points the book at an enemy. - G9 shared variables. M2 doesn't reset quest variables another quest's label also writes, so the respawned giver shows a running branch.
- G10 giver killed after the quest ended (by its own script): M2 doesn't act, the giver stays dead.
- G11 failure continues a chain. Some failures are part of a quest chain
(
LoseQuesttogether withSetUpQuestof the next quest, giver's dialog moved on); M1 must not restart those. - G12 state in dialogs (Underworld). Underworld quests keep their state in the NPCs' dialogs; a failure sets a "done/lost" dialog (or none), and M1 doesn't put the accept dialog back (7614, 10260).
- G13 named ids. Spawns with named ids (
res:AUFTRAGGEBER_10254,res:Sam1_Knappe) or the id after the type argument aren't read byInstructionScriptId; those givers aren't ing_givers. - V1/V2 vanilla bugs: 1101's time-out never ends the quest; Res:17163 is used by both 602 and 1202, and 602 deletes 1202's patient.
Per quest
Columns: how it can fail (vanilla), what happens with our mods, verdict (ok / G / finding).
| Quest | Fails by | With our mods | Verdict |
|---|---|---|---|
| 151 Tierischer Wilddieb | never (no LoseQuest); wolf Res:17081 (start script, death stirb151: bit 2, triggers the quest) |
M2/M3 on giver death: variable 151 reset to 1; if the wolf is already dead, bit 2 is lost and the wolf never respawns: stuck | G3 |
| 152 Botendienst | time limit (SetTimer 4320 -> zeit152: bit 4, LoseQuest) |
M1: bits 1 + 4 stay, the giver answers "Qfail" / "Qpostfail" without the accept button: stuck. With G1 reset: offered again; re-accept spawns the parcel (Res:6027) and later the recipient Res:17077 again (the old recipient stays, dialog off) | G1, G4 |
| 154 verschwundener Schmied | never | the script deletes the giver Res:17626 (talkedbride154, take154): after the next load M3 restarts the running quest and spawns the giver again |
G5 |
| 201 Vermisste Tochter nach Ausritt | daughter Res:18006 dies (Tochtertot201: bit 8, LoseQuest); she is spawned once (Region2Init) |
M1: bit 8 stays, giver answers okt201 then ok201: stuck. With G1: offered again, but the daughter stays dead: cannot be finished |
G1, G6 |
| 202 Eskorte für Händler | merchant Res:18012 (the giver) and bodyguard Res:18013 both dead, or the bodyguard alone at the bridge | the merchant's death is M2 (restart, respawn; his dialog has no bit tests); the bodyguard is not needed | ok |
| 203 Schatzkarte | never | giver death -> M2; re-accept creates map + chest again (old chest stays) | ok (G4) |
| 204 Die Bücher der Gelehrigkeit | never | giver death -> M2; the boss and the book come from QIS_OnEnter204, so a restart can be redone |
ok |
| 301 Orks auf Bauernhof | time limit (SetTimer 1440 -> lose301); farmer Res:17033 and daughter Res:17032 both dead |
no giver (trigger area, deleted on start); QIS_OnLose301 deletes both NPCs. M1 makes it available but nothing can start it again, and with no known giver its failed book entry is erased |
G7 |
| 302 Von Räubern und Rindern | six cattle dead (302a = 6, LoseQuest); the giver Res:17029 (escorted) dies (tot1_302) |
giver death -> M2 (but 302a is also set by startcode, so it is not "only this quest's" and keeps its count). Cattle failure -> M1: the dialog's 48(6,"302a") branch sets bit 3 -> "ok" forever: stuck, also with G1 unless G1 counts start-script initialisation as the quest's own. Re-accept spawns the six cattle again |
G1 (start-script variables), G4 |
| 303 Bodycount Orks | never; ogre Res:17031 is a one-time spawn (Region3Init, death tot303: bit 2) |
as 151: giver death resets bit 2, a dead ogre never returns: stuck | G3 |
| 401 Jagd auf wildernde Wölfe | never; wolves one-time (Region4Init, death stirb401: bit 2) |
as 151 | G3 |
| 402 Kräuter für Kräuterhexe | never | herbs from a permanent MouseEvent (Region4Init), can be picked again after M2 |
ok |
| 403 Kühe vor Wölfen retten | all cows dead (bit 4), then the giver's answer runs lose403 |
M1: bits 4 + 5 stay, giver "ok403" forever: stuck. With G1: offered again, but the cows (Region4Init) are gone |
G1, G6 |
| 501 Geister auf Landsitz | never by LoseQuest; choice change501 / nochange501 |
postchange501 turns giver Res:17071 and Res:17070 hostile with SetNPCState ... 08 12 (not Morph): M2 sees the hostility at death, but M3 after a load would restart the quest (only Morph is known as "turns") |
G8 |
| 502 Verstecktes Waffenlager | never | enemies and boss from QIS_OnEnter502 (variant by Globalchange1): redoable after M2 |
ok |
| 503 Botschaft an Geliebte | never | giver Res:17105's death label weg503 belongs to no quest (M2 does not react); not needed: the quest ends at the lover Res:17104 |
ok |
| 601 Kunstraub von Händler | never | thief Res:17135 gives the item by dialog; redoable after M2 | ok |
| 602 Wegelagerer | never | the knight Res:17136 is beaten, not killed (ritter602 sets his HP back); after M2 his dialog offers the fight again |
ok |
| 603 Entlaufener Bräutigam | never | the groom Res:17140 is beaten (braut603 heals him), the fight can be repeated after M2 |
ok |
| 701 Vergifteter Brunnen | never (lose701 is not called) |
boss Res:17063 one-time (Region7Init, drops the items); M2 resets bit 20 (item taken): stuck if the boss is dead |
G3 |
| 702 Mädchen bei Ausritt verschwunden ("Familienbande") | the girl Res:17060 dies (lose702) |
giver turned hostile and killed: handled (7ec0fa2). Girl's death -> M1: bit 1 stays, giver "Qoffen01": stuck; with G1 redoable (the girl comes from QIS_OnEnter702) |
G1 |
| 703 Objektschutz Wegbrücke | leaving the bridge area / region before the bandits are dead (zeit703: bit 4), then the giver's answer runs lose703 |
M1: bits 4 + 5 stay, giver "ok703": stuck. With G1: redoable (bandits not all dead, else the quest would have been won) | G1 |
| 801 Holzfällerstreit mit den Elfen | the giver Res:17144 dies (tod801 -> lose801) |
giver death -> M2 (restart, respawn) instead of the failure | ok |
| 802 Königliche Jäger Verschollen | never | hunters, herbs and amulet are one-time (Region8Init); M2 resets 802 (progress bits): stuck when they are used up |
G3 |
| 803 Kopfgeldjagd | never | targets one-time (Region8Init). On giver death M2 does not reset 803 (quest 801's elf dialog also sets a bit in it), so the respawned giver shows the running branch without accept and the flags say "available": stuck |
G3, G9 |
| 901 Soldaten verschleppen Frauen | time limit (zeit901, also kills quest 902's women); the women Res:17051..17054 die (lose901: bit 5), then the giver's answer runs lose901 |
M1: bit 6 stays, giver "ok901": stuck. With G1: redoable after the time limit; after the women died they are gone (Region9Init) |
G1, G6 |
| 902 Rache an Reichem Händler | never | boss Res:17049 one-time (Region9Init, death tot902: bit 2) |
G3 |
| 903 Robin Hood | never | Res:17045 is beaten and healed (re903), the choice can be made again after M2 |
ok |
| 1001 Übergriffe auf die Bevölkerung | never | boss Res:17041 one-time (Region10Init, drops the proof) |
G3 |
| 1002 Spionage | seen by the spy's group (tag 0x60 lose1002 on the NPCs from QIS_OnEnter1002: bit 4, LoseQuest) |
M1: giver sets bit 5, "ok" forever: stuck. With G1 redoable; the old group (now hostile) stays next to the new one | G1, G4 |
| 1003 Schlägertypen | the giver Res:17034 dies (verreckt1003); seven villagers die (bit 4), then the giver's answer runs lose1003 |
giver death -> M2. Villagers -> M1: bit 5, "ok" forever: stuck. With G1 redoable (the attackers come from the accept trigger again) | G1 |
| 1101 Sektenpriester opfern Jungfrauen | the virgin Res:17112 dies (Verloren1101 -> lose11a1); time limit (Zeitum1101: demon instead of the virgin, bit 3) |
death -> M1: giver sets bit 5, "ok": stuck; with G1 redoable (all from QIS_OnEnter1101, old priests stay). Time limit: vanilla never ends the quest (the giver's bit 3 branch has no LoseQuest): running forever |
G1, V1 |
| 1102 Kompromittierende Situatuion | time limit (Zeitum1102: bit 3, LoseQuest) |
M1: bit 1 stays, giver "Ok1102": stuck; with G1 redoable (the lady and the letter come from QIS_OnEnter1102). After the time limit the lady's bit 3 answer kills the giver (SetHP 0); the quest is no longer running then, so M2 does not respawn him |
G1, G10 |
| 1103 Verhandelnder Räuber | never | the robber Res:17118 is beaten and healed (tot1103) |
ok |
| 1111 DeModreys Steuerpresser | the escorted Res:17121 dies (lose1111 -> geld1111: bit 5, LoseQuest) |
M1: giver sets bit 6, "ok": stuck. With G1: the boss Res:17123 is one-time (Region111Init) and geld1111 deleted his proof Res:6051: cannot be finished |
G1, G6 |
| 1112 Animagus terrorisiert Bauernhof | the spared Animagus Res:17127 dies (ex1112 with bit 4: LoseQuest) |
M1: bit 4 stays, the giver's answer then runs postchange1112 (turns the giver hostile) instead of an offer. With G1: the Animagus is one-time (Region111Init). postchange1112 turns the giver hostile by SetNPCState (M3 after a load: G8) |
G1, G6, G8 |
| 1113 Elfischer Kunstraub | never | thief Res:17129 and the goal object Res:6052 one-time (Region111Init) |
G3 |
| 1201 Sekte beschwört kleine Dämonen | never | cult one-time (Region13Init, group dead: bit 2) |
G3 |
| 1202 Heilmittel für Händler | time limit (zeit1202 kills the patient Res:17163, LoseQuest) |
M1: giver sets bit 5, "ok": stuck. With G1 the patient (Region13Init) is dead: cannot be finished. Vanilla: quest 602's ok1_602 / ritterweg_602 walk away and delete res:17163 too (the same id): finishing 602 removes 1202's patient |
G1, G6, V2 |
| 1203 Der Richter und sein Henker | never | judge Res:17166 and executioner Res:17167 one-time (Region13Init) |
G3 |
| 1301 Entlaufener Gladiatoren-Minotaurus | never | the giver's death label is the quest's end (exit1301): attack1301 turns him hostile (M2 lets it run since 7ec0fa2), the quest ends at once (no M3). Minotaur from QIS_OnEnter1301 |
ok |
| 1302 Das Soldaten-Tunier | timer → lose1302 |
after M1 bits 4/5 and 1302a stay (G1); opponent Res:17173 is deleted by attacke1302_1 and created only by region init (G6). Vanilla typos: DelNPC res17173/res17174 (no colon), attacke1302_2 attacks 17174 |
G1 + G6 |
| 1303 Händler - legaler Warentransport | timer → lose1303 |
after M1 bits 3/4 stay (G1); re-accept creates recipient Res:17177 again (G4) | G1 + G4 |
| 1401 Händler - Warenschmuggel | the side chosen dies (lose1401) |
after M1 bits 1-6 and 1401a/1401b stay (G1); re-accept creates Res:17180/17181 again (G4). Vanilla: soldier's death label attack1401 doesn't exist (attacke1401) |
G1 + G4 |
| 1402 Junge Dame vor Übergriffen eines Offiziers schützen | never | officer and soldiers from QIS_OnEnter1402 |
ok |
| 1403 Eskortiere Händler zu geheimen Treffen | recipient after the escorted giver died (losequest1403) |
giver death is caught by M2 first (restart, giver back); re-accept creates recipient Res:17187 again (G4). Vanilla typo ok1024 |
G4 |
| 1404 Eskortiere Dame zu Treffen mit Geliebten | the lady dies (lose1404) |
after M1 bits 1/4 stay (G1); lady Res:17189 and boss Res:17190 are one-time (region init), dead lady makes a restart pointless (G6) | G1 + G6 |
| 1405 Sekte von Dämonenanbetern | never | sect leader Res:17195, cultists and the three captives are one-time (region init); M2 reset after the leader died loses the progress | G3 |
| 1501 Menschlicher Wilderer | never | the giver follows; vanilla his death (ex1501) lets the quest go on, M2 restarts it and brings him back instead. Re-accept creates the poachers again (G4) |
M2 changes vanilla + G4 |
| 1502 Hetzjagd | a label deletes the giver Res:17015, then losequest1502 |
the giver is spawned once by trigger area hetz1_1502 (deleted after use); after M1 the book points at a deleted giver and nothing spawns him again (G6). Vanilla: his death label lose1502 doesn't exist |
G6 |
| 1503 Arak-Attack | never | spiders and the target from QIS_OnEnter1503 |
ok |
| 1601 Kunstraub | never | thief from QIS_OnEnter1601 |
ok |
| 1602 Attentäter abfangen | the target dies (target1602) |
after M1 bit 4 stays (G1); target Res:17205 and assassin Res:17201 are one-time (region init), the target is dead (G6) | G1 + G6 |
| 1603 Blockadebrecher | never | ok | |
| 1701 Getrennte Liebende | the lover dies (lose1701); afterwards the giver turns hostile and fails it again (ende1701) |
after M1 bit 6 stays, the giver's dialog runs ende1701 (G1); lover Res:17209 one-time (G6); ende1701 makes the giver hostile by SetNPCState 08 12, M1 then points at an enemy (G8) |
G1 + G6 + G8 |
| 1702 Korruption | never | official Res:17215 one-time (region init) | G3 |
| 1703 Unschuldiger am Galgen | judge after the time-out (lose1703) |
after M1 bits 6/7 stay (G1); victim Res:17218 and boss Res:17221 are deleted by zeit1703, the victim is one-time (G6). lose1703 kills the giver by SetHP 0 on purpose; M2 skips his death label less1703 and brings him back |
G1 + G6, M2 changes vanilla |
| 1801 Monströsere Wilderer | never | poachers one-time (region init) | G3 |
| 1802 Dunkle Priester beschwören Dämon | never | priests from QIS_OnEnter1802 |
ok |
| 1803 Dunkelelfengift | time-out (zeitum1803) |
after M1 bit 4 stays, the giver's dialog runs losequest1803 again (G1); boss Res:17229 one-time (region init), once killed the poison can't drop again (G6) |
G1 + G6 |
| 1901 Rache an bösem Anführer in Dungeon | never | boss Res:17232 one-time (region init) | G3 |
| 1902 Monster haben Item verschleppt in Dungeon | never | monster Res:17020 one-time (region init) | G3 |
| 1903 Entlaufene 'Tochter' | the girl dies (lose1903) |
after M1 bit 5 stays, the giver's dialog morphs him into the monster at once (G1); girl Res:17237 one-time (G6) | G1 + G6 |
| 2001 Untote Kühe auf Wiesen | never | boss Res:17239 spawns on the 4th trigger area; 2001a starts at 1 from the start script, a reset to 0 matches no branch of move2001 and the boss never comes (G1 start-script variable); trigger bits in 2001 |
G3 (start-script variable) |
| 2002 Kämpfe gegen Wilde Monster | never | repeatable arena, waves from monster2_2002 |
ok |
| 2003 Anführer der Dämonensekte | never | the giver is the cult leader: QIS_OnEnter2003 makes him hostile by SetNPCState 08 12 (G8, M3 would restart). His death runs (hostile, 7ec0fa2). Vanilla typo res:174242 |
G8 |
| 2101 Hands of my Dragon | never | chain with 2102/2103 (and 2303's egg) on dragon Res:17245 (one-time); prince Res:17246 and his guards from QIS_OnEnter2101. Shared variables riesendiamant/drachenei are written by several of these quests (G9 if one is restarted) |
ok |
| 2102 Drache - Zahnstocher | never | prince is the giver; boss Res:17249 from QIS_OnEnter2102 |
ok |
| 2103 Return for Refill | never | knights created one after the other by ziel2103 |
ok |
| 2201 Kuss der Spinnefrau | the girl dies (lose2201) |
after M1 bits stay (G1); girl Res:17283 one-time (G6); postchange2201 turns the giver Res:17281 hostile by SetNPCState 08 12 (G8) |
G1 + G6 + G8 |
| 2202 Narzisstische Zauberin | never | change2202 turns the giver Res:17255 hostile by SetNPCState 08 12 (G8) |
G8 |
| 2203 Hinterhältiger Giftmischer | never | poisoner Res:17260 and the six barrels (counter 2303a) are one-time (region init) |
G3 |
| 2301 Besorge Reagentium | never | bush is a fixed MouseEvent, item re-created in OnEnter | ok |
| 2302 Larbortiere | never | the four monsters are one-time (region init), counted in 2302b |
G3 |
| 2401 Botschaft für Scouts | never | chain 2401-2404 on giver Res:17268 (his death label mann2404 belongs to 2404); scouts one-time (region init), moved/morphed by the quest |
G3 |
| 2402 Verlaufene Sielder finden | the settler dies after joining (losequest2402) |
the failure continues the chain (SetUpQuest 2403, giver's dialog set to 2403); M1 restarting 2402 is wrong (G11) |
G11 |
| 2403 Verschleppte Sielder befreien | all settlers die (losequest2403) |
like 2402: the failure continues the chain with 2404 (G11) | G11 |
| 2404 Verteidige Lager | never | vanilla the giver's death (mann2404) hands the reward to Res:17280; M2 restarts and brings him back instead |
M2 changes vanilla |
| 2411 Das Orkische Relikt | never | relic from QIS_OnEnter2411 |
ok |
| 2412 Der Feige Hund | never | dog Res:17584 one-time (region init) | G3 |
| 2413 Kleine Wuselorks | never | all from QIS_OnEnter2413 |
ok |
| 2501 Finde Drachnschuppe für Rüstung | never | dragon Res:17292 one-time (region init); counts towards finale |
G3 |
| 2502 Eierdieb | the time-out, reported to the giver (losequest2502) |
the failure counts towards the region's finale (bit 2 + finalestart) like a success (G11); after M1 bits 4/5 stay (G1) |
G11 |
| 2503 Drachentöter vertreiben | never | dragon slayers one-time (region init) | G3 |
| 2504 Rette Jungfrau | the maiden (= giver) dies (lose2504) |
M2 catches her death first: restart and respawn instead of failure + finale bit; redoable |
M2 changes vanilla |
| 9003 Versteckter Händler | rg3_goodie1_lose (merchant's death) |
progress lives in the shared variable goodies (8 quests), M1/M2 can't reset it (G1 + G9): after M1 bit 1 stays and the dialog offers the reward branch (ExitQuest) without the quest running |
G1 + G9 |
| 9004 Vermisstes Kind | rg1_goodie_lose (child's death) |
goodies bit 4 stays, the giver only answers "ok" (G1 + G9); child Res:17513 one-time (G6) |
G1 + G6 + G9 |
| 9005 Der Waldläufer | never | ok | |
| 9006 Der unbekannte Krieger | never | progress in shared goodies |
ok |
| 9007 Jacquaire's Waffen | never | guards from QIS_OnEnter9007 |
ok |
| 9008 Furchtbares Verbrechen | escorted giver Res:17539 dies (losequest9008) |
M2 catches the death (restart, respawn); QIS_OnEnter9008 sets the trigger area again |
M2 changes vanilla |
| 9009 Whiskeylieferung | never | ok | |
| 9010 Vergrabene Sklaven | escorted giver Res:17575 dies (lose9010) |
M2 restarts; but 9010 is a counter (0 = offer, needs key Res:17580 in the inventory), M2's reset to 1 shows the "follow" branch, and QIS_OnEnter9010 deleted the key, so it can't be accepted again (G6) |
G6 |
| 9011 Jacquaires Vergangenheit | never | boss and target from QIS_OnEnter9011 |
ok |
| main quests 1-81, 670 | never | started by trigger areas (SelfTriggerQuest<N>), no giver, so M1-M3 don't touch them; 31's giver is only set by SetNPCState (not in g_givers) |
ok |
| 65 Trockenlegung durch Zwergenstaudamm (main) | never | giver Res:18306 (Torfstecher, start script) is in g_givers. Vanilla his death leaves 65 unfinishable (61 is activated by Exit65); M2 brings him back, but resets 65 incl. bit 5 (pump switched by SwitchPump65); if the pump can't be used twice the quest is stuck (G3). Re-accept creates the rune Res:17569 again (G4) |
G3 + G4 |
| 210 Verschleppte Novizinnen in Räuberöhle | never | boss Res:17083 one-time (start script) | G3 |
| 9000 Das Untotenlager | the shaman's drop is picked up while the quest runs | refusing makes the giver Res:17500 attackable by SetNPCState 08 14 (not Morph, G8); killing him drops the item whose label opens the Khorad Nur gate (ablehnensieg_goodie_wueste). If M2 sees him as not hostile it skips drop_goodie_wueste: no item, the gate (main quest 55's way) never opens. Check IsHostileTo for 08 14 |
G8, critical |
| 5003 Opferritual | the hero refuses at the end (nein5003) |
a story choice: the shaman Res:17699 and his tribe turn hostile (SetNPCState 08 12) and the quest fails. M1 restarts it with bit 6 kept, so the (now hostile) shaman would offer the choice again (G11 + G8) |
G8 + G11 |
| 5005 Pony Express | a time limit runs out (losepe) |
losepe deletes the giver Res:17753 (spawned once by main quest label NachOrkland55) and all stations; after M1 the book points at nobody and the quest can't be taken again (G5/G6); 5005c stays (G1) |
G1 + G5 |
| 6001 Die Invasion der Eiselfen | all elves of the camp die (od_welfen6001) |
after M1 bits stay (G1); the elves (incl. giver Res:17706) are one-time, dead (G6); re-accept creates the invaders again (G4). Accept label starts with SetNPCState, so the giver isn't in g_givers (no M2/M3) |
G1 + G4 + G6 |
| 6002 Das Orklager | never | ok | |
| 6003 Elfenbeschützer | the escorted elf Res:17750 dies (lose6003) |
after M1 bit 3 stays (G1); the elf is one-time (G6); her dialog is set by SetNPCState, so she is probably not in g_givers (no M2) |
G1 + G6 |
| 2600-3599 generic quests (16 templates × 22 regions) | DQ_RG<n>_..._LOSE_<id> (and _ABORT_ for escorts) |
no giver (runtime-assigned NPC), so no M2/M3; M1 restarts them although Quest_End already copies them (G2) |
G2 |
Underworld (bin\Addon\NetScriptCamp)
Underworld quests keep their state in the NPCs' dialogs (SetNPCState ... dialog"dlg_<npc>_<id>_<step>"), rarely in variables, and most givers are
spawned by QIS_OnSetUp<id> (run from the start script) without a dialog.
| Quest | Fails when | Finding | Class |
|---|---|---|---|
| 7612 Eskorte | escorted Nanoduk Res:19547 dies (od_nanoduk) |
he is the giver and one-time (QIS_OnSetUp7612); after M1 nobody offers the quest (G6) |
G6 |
| 7614 Vermisstes Kind (Underworld) | the child Res:19549 dies (od_erdriac) |
the giver's dialog is set to the "child is dead" step _d (only "ok"); M1 doesn't restore the accept dialog _a, so it can't be taken again (G12). The child comes from QIS_OnEnter7614 |
G12 |
| 7617 Eskorte in den Süden | escorted giver Res:19586 dies (od_7617) |
he is spawned with his accept dialog, so M2 catches his death: restart and respawn | M2 changes vanilla |
| 7619 Tod den Toten | the giver Res:19545 dies (od_threepwood_7619) |
his accept dialog is only set by SetNPCState in QIS_OnSetUp7619 (not in g_givers); after M1 he is dead (G6) |
G6 |
| 9518 Unter der Herrschaft von Dämonen | the mother Res:19530 dies while following (od_lose9518) |
after M1 bits 1/2/4 stay, the giver only answers "ok" (G1); re-accept creates mother and demons again (G4) | G1 + G4 |
| 9520 Cookies Quest | the hero gives the cookies to Von Endlich, then the girl ends it (btn_FinishLose9520, gold for experience) |
a story choice (G11); after M1 bit 4 stays, so the girl offers btn_FinishLose9520 again and again (repeatable gold-for-experience trade) |
G11 |
| 10254 Der Hilferuf | the giver dies (od_Auftraggeber_10254) |
the giver is spawned once when the letter is picked up (ot_Brief_10254); after M1 he's dead and the letter gone (G6). The 10250-10261 givers have named ids (res:AUFTRAGGEBER_10254, after the type argument), which InstructionScriptId doesn't read: none of them is in g_givers (G13) |
G6 + G13 |
| 10255 Panik vor Spinnen | never (its "lose" is a label name; the giver offers a restart himself) | ok | |
| 10260 Das Rätsel in der Wüßte | the wrong chest is opened (fillchest_chestQJ_0x) |
the giver's dialog is removed (0a#0); after M1 nobody offers it (G12) |
G12 |
| other Underworld quests (main 11-56, 7600-7630, 9511-9522, 9900, 11101-11110, 15001-15084) | never | main quests have no giver (untouched). Side quests: givers spawned with their accept dialog in QIS_OnSetUp<id> are in g_givers (7600, 7601, 7605, 7609, 7614, 7617, 7618, 7620, 7622-7624, 7626, 7630, 9511, 9513, 9515, 9518, 9520, 9521); a chain's later quests on the same giver (dialog by SetNPCState) are not. Their targets also come from QIS_OnSetUp (one-time), so M2 after a target died loses progress only where variables hold it (G3, rare here); named ids (res:Sam1_Knappe, res:AUFTRAGGEBER_…) are skipped (G13) |
ok / G3 |
Summary and proposed fixes
Counted over the side quests (Ancaria 151-2504, 9003-9011, 210, 65, the 5003-6003 set and the Underworld quests that can fail): about a third are fine, the rest fall into the classes above. In order of impact:
- G8 critical, 9000 (Khorad Nur gate): verify by a log whether a creature
set by
SetNPCState ... 08 14is hostile to the hero (IsHostileTo). If not, M2 skips the shaman's death label and the gate never opens. Fix either way: treat a giver as "turned" when any of its quest's labels set08 12/08 14on it (extendsScanGiverTurnsbeyond Morph); that also fixes M3 for 1112, 1301, 1701, 2003, 2201, 2202, 501, 5003. - G1 reset on failure: M1 resets the quest's own variables like M2 (including the ones only start/region scripts initialise, with their initial values, e.g. 302a, 2001a = 1). Fixes most "giver only says ok" cases (152, 702, 703, 1002, 1003, 1302, 1303, 1401, 1404, 1602, 1803, 1903, 9518, ...).
- G11 failures that are part of a story or chain (2402, 2403, 2502,
5003, 9520): M1 must not restart a quest whose failure label also calls
SetUpQuest/finalestart, or sets the giver hostile. - G2 generic quests: M1 leaves 2600-3599 (and their runtime copies) to the game.
- G6 restart without NPCs / G3 lost progress: the bigger design question. Options: (a) on restart, respawn the quest's one-time NPCs from their spawn instructions in start/region scripts (like the giver), (b) keep the variables on M2/M3 (no progress loss, but the giver may answer with a running branch), (c) don't restart quests whose needed NPCs are gone and leave them failed. Recommendation: (a) for NPCs the quest's dialogs or death labels name, else (c).
- G4 duplicates: before re-running
QIS_OnEnter, delete the quest's still-alive named NPCs/objects it is about to create. - G5/G7 (154, 301, 1502, 5005): M3 skips quests whose labels
DelNPCtheir giver; M1 skips quests without a giver. - G9/G12/G13 (803, 9003/9004
goodies, 7614, 10260, named ids): lower priority; G12 needs the accept dialog put back (it is in the giver's spawn instruction orQIS_OnSetUp).
Fixes (2026-10-30)
Request: "all, but leave 1, as i cant play for now" (2-8 above; G8 waits for a measurement in the game). Not yet tested in the game.
mods/questscript.cpp(new) reads the script code once and keeps, per quest: the giver (spawned with the accept dialog, else given it by an NPC state instruction: the Underworld'sQIS_OnSetUp<id>), its variables (set only by its labels, plus the one named after it: G9), whatQIS_OnEnter<id>creates, the NPCs it needs (its labels set their state, don't create them), whether it morphs or deletes its giver, and the failure labels that end its story (LoseQuestwithSetUpQuest/ActivateQuest, experience or gold, a call into another quest's label, or an NPC offering the quest turned hostile or set to 0 hit points: 1701ende1701, 1703, 2402, 2403, 2502, 2504, 5003, 9520). It also keeps the labels running (forQuest_End) and spawns NPCs once their bodies are gone.questfail.cpp: atQuest_Trigger(first time) the quest's variables are kept ("questVariables" with the hero). A failed quest stays failed when it is a generic quest or a copy (G2), has no giver (G7), its failure ends the story (G11) or its giver / an NPC it needs is gone without a spawn instruction (G5/G6). Else the restart also: resets its variables to the kept values (G1; without them: 1 for the one named after the quest, 0 else), deletes whatQIS_OnEntercreated (G4), spawns dead needed NPCs and the giver again (G6, from region start labels, another quest's label orQIS_OnSetUp), and gives a living giver the accept dialog again (G12). After a load, failed quests restarted earlier get their variables reset (repairs saves stuck by G1).questgiver.cppuses the same scan; the load repair skips quests that delete their giver (G5); the giver comes back throughquestfail::Restart.- Not done: G8 (fix 1), G3 for progress held in one-time objects (2203's
barrels), G10, G13 (named ids such as
res:AUFTRAGGEBER_10254: the game's name table is unknown, those givers can't be checked or respawned).