diff --git a/src/005-passages/interactPassages.js b/src/005-passages/interactPassages.js
index 67177809d720b45a1f3feff68d26ac6b18a69933..d753a4f12fae893f5449aad21d2a93c47a2d2eec 100644
--- a/src/005-passages/interactPassages.js
+++ b/src/005-passages/interactPassages.js
@@ -333,4 +333,11 @@ new App.DomPassage("Walk Past List",
 		V.nextLink = "Main";
 		return App.UI.walkPastAll();
 	}
-);
\ No newline at end of file
+);
+new App.DomPassage("Find Slave",
+	() => {
+		V.nextButton = "Back to Main";
+		V.nextLink = "Main";
+		return App.findSlave.passage();
+	}, ["jump-to-safe", "jump-from-safe"]
+);
diff --git a/src/js/findSlave.js b/src/js/findSlave.js
index 44796f307e084795873bc16d3f85a8998524ba47..186e28afa0dd100d85ce28626c7175e5e2929d70 100644
--- a/src/js/findSlave.js
+++ b/src/js/findSlave.js
@@ -90,3 +90,46 @@ App.FindSlave.searchByExpression = function(query) {
 	}
 	return frag;
 };
+
+App.FindSlave.passage = function() {
+	const node = new DocumentFragment();
+
+	App.UI.DOM.appendNewElement("p", node, `After spending a minute trying to remember some details about one of your slaves, you sit down behind your desk and tell ${assistant.name} that you need to locate a particular slave's records.`);
+
+	App.UI.DOM.appendNewElement("p", node, `"Certainly, ${properMaster()}. What can you tell me about them?"`);
+
+	App.Events.addParagraph(node, [
+		`"They're called something like:`,
+		App.UI.DOM.makeTextBox(V.findName, v => V.findName = v),
+		App.UI.DOM.link(
+			"Locate",
+			() => $(slaveList).empty().append(App.FindSlave.searchByName(V.findName))
+		),
+		App.UI.DOM.makeElement("div", `(Enter a fragment of their nickname, name, surname, birth name, or birth surname)`, "note")
+	]);
+
+	App.Events.addParagraph(node, [
+		`"In the past, they were:`,
+		App.UI.DOM.makeTextBox(V.findBackground, v => V.findBackground = v),
+		App.UI.DOM.link(
+			"Locate",
+			() => $(slaveList).empty().append(App.FindSlave.searchByName(V.findBackground))
+		),
+		App.UI.DOM.makeElement("div", `(Enter a fragment of their origin or past job, for example, "shelter" or "lawyer")`, "note")
+	]);
+
+	App.Events.addParagraph(node, [
+		`"Their data should meet this condition:`,
+		App.UI.DOM.makeTextBox(V.findData, v => V.findData = v),
+		App.UI.DOM.link(
+			"Locate",
+			() => $(slaveList).empty().append(App.FindSlave.searchByName(V.findData))
+		),
+		App.UI.DOM.makeElement("div", `(Enter a conditional expression which evaluates to true for the slave you want to find, such as "slave.physicalAge >= 18 && slave.physicalAge < 21")`, "note")
+	]);
+
+	const slaveList = App.UI.DOM.appendNewElement("span", node); // results list gets populated here by jQuery
+
+	return node;
+};
+
diff --git a/src/npc/findSlave.tw b/src/npc/findSlave.tw
deleted file mode 100644
index e7aebb3b75b9076c0e94cb51891a4b38d3a95018..0000000000000000000000000000000000000000
--- a/src/npc/findSlave.tw
+++ /dev/null
@@ -1,32 +0,0 @@
-:: Find Slave [nobr jump-to-safe jump-from-safe]
-
-<<set $nextButton = "Back to Main", $nextLink = "Main">>
-
-After spending a minute trying to remember some details about one of your slaves, you sit down behind your desk and tell $assistant.name that you need to locate a particular slave's records.<br><br>
-
-"Certainly, <<= properMaster()>>. What can you tell me about them?"<br><br>
-
-"They're called something like:
-<<textbox "$findName" $findName autofocus>>
-<<link "Locate">>
-	<<script>>$('#slaveList').empty().append(App.FindSlave.searchByName(V.findName));<</script>>
-<</link>>
-<br>//(Enter a fragment of their nickname, name, surname, birth name, or birth surname)//<br><br>
-
-"In the past, they were:
-<<textbox "$findBackground" $findBackground>>
-<<link "Locate">>
-	<<script>>$('#slaveList').empty().append(App.FindSlave.searchByBackground(V.findBackground));<</script>>
-<</link>>
-<br>//(Enter a fragment of their origin or past job, for example, "shelter" or "lawyer")//<br><br>
-
-"Their data should meet this condition:
-<<textbox "$findData" $findData>>
-<<link "Locate">>
-	<<script>>$('#slaveList').empty().append(App.FindSlave.searchByExpression(V.findData));<</script>>
-<</link>>
-<br>//(Enter a conditional expression which evaluates to true for the slave you want to find, such as "slave.physicalAge >= 18 && slave.physicalAge < 21")//<br><br>
-
-<span id="slaveList">
-	/* results list gets populated here by jQuery */
-</span>