diff --git a/src/js/findSlave.js b/src/js/findSlave.js new file mode 100644 index 0000000000000000000000000000000000000000..0e5b447910136478d2e386764ad3ec676c1fd9c9 --- /dev/null +++ b/src/js/findSlave.js @@ -0,0 +1,59 @@ +App.FindSlave = {}; + +/** + * Fragment searching: See if every needle can found somewhere in the field of haystacks + * @param {string[]} haystacks + * @param {RegExp[]} needles + * @returns {boolean} + */ +App.FindSlave._fragmentSearch = function(haystacks, needles) { + const hs = haystacks.join(" "); + return needles.every((needle) => { return needle.test(hs); }); +}; + +/** + * Get slave indices which match a predicate + * @param {function} predicate + * @returns {number[]} + */ +App.FindSlave._slaveIndices = function(predicate) { + return V.slaves.reduce((acc, slave, ind) => { + if (predicate(createReadonlyProxy(slave))) { + acc.push(ind); + } + return acc; + }, []); +}; + +/** + * Generate a slave list as the result of fragment searching all the name-type fields + * @param {string} query + * @returns {DocumentFragment} + */ +App.FindSlave.searchByName = function(query) { + const needles = query.split(" ").map((needle) => { return new RegExp(needle, "i"); }); + const indices = this._slaveIndices((slave) => { return this._fragmentSearch([slave.slaveName, slave.slaveSurname, slave.birthName, slave.birthSurname], needles); }); + return App.UI.SlaveList.render.listDOM(indices, [], App.UI.SlaveList.SlaveInteract.stdInteract); +}; + +/** + * Generate a slave list as the result of fragment searching profession and origin + * @param {string} query + * @returns {DocumentFragment} + */ +App.FindSlave.searchByBackground = function(query) { + const needles = query.split(" ").map((needle) => { return new RegExp(needle, "i"); }); + const indices = this._slaveIndices((slave) => { return this._fragmentSearch([slave.career, slave.origin], needles); }); + return App.UI.SlaveList.render.listDOM(indices, [], App.UI.SlaveList.SlaveInteract.stdInteract); +}; + +/** + * Generate a slave list as the result of evaluating an expression + * @param {string} query + * @returns {DocumentFragment} + */ +App.FindSlave.searchByExpression = function(query) { + const pred = new Function("slave", "return (" + query + ");"); + const indices = runWithReadonlyProxy(() => { return this._slaveIndices(pred); }); + return App.UI.SlaveList.render.listDOM(indices, [], App.UI.SlaveList.SlaveInteract.stdInteract); +}; diff --git a/src/uncategorized/findSlave.tw b/src/uncategorized/findSlave.tw new file mode 100644 index 0000000000000000000000000000000000000000..991d56cb61dea865aa93a15d36472e3396e5e589 --- /dev/null +++ b/src/uncategorized/findSlave.tw @@ -0,0 +1,32 @@ +:: Find Slave [nobr] + +<<set $nextButton = "Back to Main", $nextLink = "Main", $showEncyclopedia = 0>> + +After spending a minute trying to remember some details about one of your slaves, you sit down behind your desk and tell $assistantName 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 "_nameSearch" "" autofocus>> +<<link "Locate">> + <<script>>$('#slaveList').empty().append(App.FindSlave.searchByName(State.temporary.nameSearch));<</script>> +<</link>> +<br>//(Enter a fragment of their nickname, name, surname, birth name, or birth surname)//<br><br> + +"In the past, they were: +<<textbox "_backgroundSearch" "">> +<<link "Locate">> + <<script>>$('#slaveList').empty().append(App.FindSlave.searchByBackground(State.temporary.backgroundSearch));<</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 "_dataSearch" "">> +<<link "Locate">> + <<script>>$('#slaveList').empty().append(App.FindSlave.searchByExpression(State.temporary.dataSearch));<</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> diff --git a/src/uncategorized/storyCaption.tw b/src/uncategorized/storyCaption.tw index 2b58dccd294e4df2728f0471ea874f7b7a0438b0..ae1184e974f4ed04861c314c488080a8831e1db4 100644 --- a/src/uncategorized/storyCaption.tw +++ b/src/uncategorized/storyCaption.tw @@ -539,6 +539,12 @@ <<if ($corpSpecToken > 0) && ($corpSpecTimer == 0)>>@@.yellow;[!]@@<</if>> <</if>> + <<if _Pass != "Find Slave">> + <span id="findSlave"> <br> + <<link [[Locate Slave|Find Slave]]>><</link>> + </span> + <</if>> + <<if $sideBarOptions.compact === 0 && _Pass === "Main" || $sideBarOptions.compact === 1 && _Pass === "Manage Arcology">> <br> <<if $FSAnnounced>> <span id="FSButton"> <br>