mirror of
https://github.com/raeleus/Hashtag-DnD.git
synced 2025-07-19 11:14:45 -04:00
Added hashtags for locations.
This commit is contained in:
parent
2507e38739
commit
5a1d9c2f36
4 changed files with 220 additions and 2 deletions
149
Input.js
149
Input.js
|
@ -52,6 +52,12 @@ const showAutoXpSynonyms = ["showautoxp"]
|
|||
const setDefaultDifficultySynonyms = ["setdefaultdifficulty", "defaultdifficulty", "setdefaultdc", "defaultdc", "setdefaultac", "defaultac", "setdifficulty", "difficulty", "dc"]
|
||||
const showDefaultDifficultySynonyms = ["showdefaultdifficulty", "showdefaultdc", "showdefaultac"]
|
||||
const generateNameSynonyms = ["generatename", "name", "randomname", "makename", "createname"]
|
||||
const createLocationSynonyms = ["createlocation", "makelocation", "generatelocation", "createplace", "makeplace", "generateplace", "createtown", "maketown", "generatetown", "createvillage", "makevillage", "generatevillage", "createcity", "makecity", "generatecity", "updatelocation", "updateplace", "updatetown", "updatevillage", "updatecity"]
|
||||
const goToLocationSynonyms = ["gotolocation", "golocation", "movetolocation", "traveltolocation", "travellocation", "gotoplace", "goplace", "movetoplace", "traveltoplace", "travelplace", "gototown", "gotown", "movetotown", "traveltotown", "traveltown", "gotovillage", "govillage", "movetovillage", "traveltovillage", "travelvillage", "gotocity", "gocity", "movetocity", "traveltocity", "travelcity", "goto", "go", "moveto", "move", "travelto", "travel"]
|
||||
const removeLocationSynonyms = ["removelocation", "deletelocation", "eraselocation", "removeplace", "deleteplace", "eraseplace", "removetown", "deletetown", "erasetown", "removevillage", "deletevillage", "erasevillage", "removecity", "deletecity", "erasecity"]
|
||||
const showLocationsSynonyms = ["showlocations", "showplaces", "showtowns", "showvillages", "showcities", "locations", "places", "towns", "villages", "cities"]
|
||||
const getLocationSynonyms = ["getlocation", "location", "getcoordinates", "coordinates", "getcoords", "coords", "showlocation"]
|
||||
const clearLocationsSynonyms = ["clearlocations", "eraselocations", "deletelocations", "resetlocations"]
|
||||
const helpSynonyms = ["help"]
|
||||
|
||||
const modifier = (text) => {
|
||||
|
@ -84,7 +90,7 @@ const modifier = (text) => {
|
|||
return { text }
|
||||
}
|
||||
|
||||
if (!found) found = processCommandSynonyms(command, commandName, helpSynonyms.concat(rollSynonyms, noteSynonyms, eraseNoteSynonyms, showNotesSynonyms, clearNotesSynonyms, showCharactersSynonyms, removeCharacterSynonyms, generateNameSynonyms, setDefaultDifficultySynonyms, showDefaultDifficultySynonyms, renameCharacterSynonyms, cloneCharacterSynonyms, resetSynonyms), function () {return true})
|
||||
if (!found) found = processCommandSynonyms(command, commandName, helpSynonyms.concat(rollSynonyms, noteSynonyms, eraseNoteSynonyms, showNotesSynonyms, clearNotesSynonyms, showCharactersSynonyms, removeCharacterSynonyms, generateNameSynonyms, setDefaultDifficultySynonyms, showDefaultDifficultySynonyms, renameCharacterSynonyms, cloneCharacterSynonyms, createLocationSynonyms, showLocationsSynonyms, goToLocationSynonyms, removeLocationSynonyms, getLocationSynonyms, clearLocationsSynonyms, resetSynonyms), function () {return true})
|
||||
|
||||
if (found == null) {
|
||||
if (state.characterName == null) {
|
||||
|
@ -150,6 +156,12 @@ const modifier = (text) => {
|
|||
if (text == null) text = processCommandSynonyms(command, commandName, setDefaultDifficultySynonyms, doSetDefaultDifficulty)
|
||||
if (text == null) text = processCommandSynonyms(command, commandName, showDefaultDifficultySynonyms, doShowDefaultDifficulty)
|
||||
if (text == null) text = processCommandSynonyms(command, commandName, generateNameSynonyms, doGenerateName)
|
||||
if (text == null) text = processCommandSynonyms(command, commandName, createLocationSynonyms, doCreateLocation)
|
||||
if (text == null) text = processCommandSynonyms(command, commandName, goToLocationSynonyms, doGoToLocation)
|
||||
if (text == null) text = processCommandSynonyms(command, commandName, clearLocationsSynonyms, doClearLocations)
|
||||
if (text == null) text = processCommandSynonyms(command, commandName, removeLocationSynonyms, doRemoveLocation)
|
||||
if (text == null) text = processCommandSynonyms(command, commandName, showLocationsSynonyms, doShowLocations)
|
||||
if (text == null) text = processCommandSynonyms(command, commandName, getLocationSynonyms, doGetLocation)
|
||||
if (text == null) text = processCommandSynonyms(command, commandName, renameCharacterSynonyms, doRenameCharacter)
|
||||
if (text == null) text = processCommandSynonyms(command, commandName, cloneCharacterSynonyms, doCloneCharacter)
|
||||
if (text == null) text = processCommandSynonyms(command, commandName, helpSynonyms, doHelp)
|
||||
|
@ -518,6 +530,9 @@ function init() {
|
|||
}
|
||||
if (state.characters == null) state.characters = []
|
||||
if (state.notes == null) state.notes = []
|
||||
if (state.locations == null) state.locations = []
|
||||
if (state.x == null) state.x = 0
|
||||
if (state.y == null) state.y = 0
|
||||
if (state.autoXp == null) state.autoXp = 0
|
||||
if (state.defaultDifficulty == null) state.defaultDifficulty = 10
|
||||
state.show = null
|
||||
|
@ -1163,6 +1178,134 @@ function doShowNotes(command) {
|
|||
return " "
|
||||
}
|
||||
|
||||
function doCreateLocation(command) {
|
||||
var locationArgIndex = 2
|
||||
|
||||
var arg0 = getArgument(command, 0)
|
||||
var arg1 = getArgument(command, 1)
|
||||
if (arg0 == null || isNaN(arg0)) {
|
||||
arg0 = null
|
||||
arg1 = null
|
||||
locationArgIndex = 0
|
||||
}
|
||||
|
||||
if (arg0 != null && (arg1 == null || isNaN(arg1))) {
|
||||
arg1 = null
|
||||
locationArgIndex = 1
|
||||
}
|
||||
|
||||
var arg2 = getArgumentRemainder(command, locationArgIndex)
|
||||
if (arg2 == null) {
|
||||
state.show = "none"
|
||||
return "\n[Error: Not enough parameters. See #help]\n"
|
||||
}
|
||||
|
||||
var location = createLocation(arg0, arg1, arg2)
|
||||
|
||||
state.show = "none"
|
||||
return `\n[Location ${toTitleCase(arg2)} has been created at (${location.x},${location.y})]\n`
|
||||
}
|
||||
|
||||
function doGoToLocation(command) {
|
||||
var character = getCharacter()
|
||||
var characterName = character == null ? "You" : character.name
|
||||
var possessiveName = getPossessiveName(characterName)
|
||||
var travelWord = characterName == "You" ? "travel" : "travels"
|
||||
var locationArgIndex = 2
|
||||
|
||||
var arg0 = getArgument(command, 0)
|
||||
var arg1 = getArgument(command, 1)
|
||||
|
||||
if (arg0 == null || isNaN(arg0)) {
|
||||
arg0 = state.x
|
||||
arg1 = state.y
|
||||
locationArgIndex = 0
|
||||
}
|
||||
|
||||
if (arg0 != null && (arg1 == null || isNaN(arg1))) {
|
||||
arg1 = state.y
|
||||
locationArgIndex = 1
|
||||
}
|
||||
|
||||
var distance = 0
|
||||
var location
|
||||
var locationName = getArgumentRemainder(command, locationArgIndex)
|
||||
if (locationName == null && locationArgIndex == 0) {
|
||||
state.show = none
|
||||
return "\n[Error: Not enough parameters. See #help]\n"
|
||||
}
|
||||
|
||||
if (locationName == null) {
|
||||
var index = state.locations.findIndex(x => x.x == arg0 && x.y == arg1)
|
||||
if (index != -1) location = state.locations[index]
|
||||
} else {
|
||||
var index = state.locations.findIndex(x => x.name.toLowerCase() == locationName.toLowerCase())
|
||||
if (index != -1) location = state.locations[index]
|
||||
else location = createLocation(arg0, arg1, locationName)
|
||||
}
|
||||
|
||||
if (location == null) {
|
||||
distance = pointDistance(state.x, state.y, arg0, arg1)
|
||||
state.x = arg0
|
||||
state.y = arg1
|
||||
} else {
|
||||
distance = pointDistance(state.x, state.y, location.x, location.y)
|
||||
state.x = location.x
|
||||
state.y = location.y
|
||||
state.location = location.name
|
||||
}
|
||||
distance = distance.toFixed(1)
|
||||
|
||||
state.show = "none"
|
||||
if (location == null) return `\n${characterName} ${travelWord} ${distance > 0 ? distance + " units " : ""} to (${arg0},${arg1})`
|
||||
if (state.characters.length > 1) return `\n${possessiveName} party travels ${distance > 0 ? distance + " units " : ""}to ${toTitleCase(location.name)} at (${location.x},${location.y})\n`
|
||||
return `\n${characterName} ${travelWord} ${distance > 0 ? distance + " units " : ""}to ${toTitleCase(location.name)} at (${location.x},${location.y})\n`
|
||||
}
|
||||
|
||||
function doGetLocation(command) {
|
||||
state.show = "none"
|
||||
return `\n[You are at ${state.location == null ? "" : "the location " + state.location + " "}(${state.x},${state.y})]`
|
||||
}
|
||||
|
||||
function doClearLocations(command) {
|
||||
state.locations = []
|
||||
state.location = null
|
||||
|
||||
state.show = "none"
|
||||
return "\n[The locations have been cleared]\n"
|
||||
}
|
||||
|
||||
function doRemoveLocation(command) {
|
||||
var arg0 = getArgumentRemainder(command, 0)
|
||||
if (arg0 == null) {
|
||||
state.show = "none"
|
||||
return "\n[Error: Not enough parameters. See #help]\n"
|
||||
}
|
||||
|
||||
var location
|
||||
if (isNaN(arg0)) arg0 = state.locations.findIndex(x => x.name.toLowerCase() == arg0.toLowerCase())
|
||||
else arg0--
|
||||
|
||||
if (arg0 == -1) {
|
||||
state.show = "none"
|
||||
return "\n[Error: Location not found. See #showlocations]\n"
|
||||
} else if (arg0 >= state.locations.length || arg0 < 0) {
|
||||
state.show = "none"
|
||||
return "\n[Error: Location number out of bounds. See #showlocations]\n"
|
||||
} else {
|
||||
location = state.locations[arg0]
|
||||
state.locations.splice(arg0, 1)
|
||||
}
|
||||
|
||||
state.show = "none"
|
||||
return `\n[The location ${toTitleCase(location.name)} has been removed]\n`
|
||||
}
|
||||
|
||||
function doShowLocations(command) {
|
||||
state.show = "locations"
|
||||
return " "
|
||||
}
|
||||
|
||||
function doTake(command) {
|
||||
var arg0 = getArgument(command, 0)
|
||||
if (arg0 == null) {
|
||||
|
@ -1794,6 +1937,10 @@ function doClearSkills(command) {
|
|||
function doReset(command) {
|
||||
state.notes = []
|
||||
state.characters = []
|
||||
state.locations = []
|
||||
state.location = null
|
||||
state.x = 0
|
||||
state.y = 0
|
||||
state.defaultDifficulty = null
|
||||
state.autoXp = null
|
||||
|
||||
|
|
48
Library.js
48
Library.js
|
@ -17,6 +17,52 @@ function shuffle(array, seed) {
|
|||
}
|
||||
}
|
||||
|
||||
function pointDistance(x1, y1, x2, y2) {
|
||||
return Math.sqrt(Math.pow(x1 - x2, 2) + Math.pow(y1 - y2, 2))
|
||||
}
|
||||
|
||||
function rotate(cx, cy, x, y, angle) {
|
||||
var radians = (Math.PI / 180) * angle
|
||||
var cos = Math.cos(radians)
|
||||
var sin = Math.sin(radians)
|
||||
var nx = (cos * (x - cx)) + (sin * (y - cy)) + cx
|
||||
var ny = (cos * (y - cy)) - (sin * (x - cx)) + cy
|
||||
return [nx, ny];
|
||||
}
|
||||
|
||||
function createLocation(x, y, name) {
|
||||
if (x == null || y == null) {
|
||||
var cx = x == null ? state.x : x
|
||||
var cy = y == null ? state.y : y
|
||||
var coords = rotate(cx, cy, getRandomInteger(-10, 10) + cx, cy, Math.random() * 360)
|
||||
x = coords[0]
|
||||
y = coords[1]
|
||||
}
|
||||
|
||||
x = Math.round(x)
|
||||
y = Math.round(y)
|
||||
|
||||
var existingLocationIndex = state.locations.findIndex(element => element.name.toLowerCase() == name.toLowerCase())
|
||||
var location
|
||||
if (existingLocationIndex == -1) {
|
||||
location = {
|
||||
x: x,
|
||||
y: y,
|
||||
name: name
|
||||
}
|
||||
state.locations.push(location)
|
||||
} else {
|
||||
location = state.locations[existingLocationIndex]
|
||||
location.x = x
|
||||
location.y = y
|
||||
location.name = name
|
||||
}
|
||||
|
||||
addStoryCard(location.name, "", "location")
|
||||
|
||||
return location
|
||||
}
|
||||
|
||||
function sanitizeText(text) {
|
||||
if (/^\s*>.*says? ".*/.test(text)) {
|
||||
text = text.replace(/^\s*>\s/, "")
|
||||
|
@ -175,7 +221,7 @@ function calculateRoll(rolltext) {
|
|||
function getCharacter(characterName) {
|
||||
if (characterName == null) characterName = state.characterName
|
||||
if (characterName == null) return null
|
||||
return state.characters.find((element) => element.name.toLowerCase() == characterName.toLowerCase())
|
||||
return state.characters.find(element => element.name.toLowerCase() == characterName.toLowerCase())
|
||||
}
|
||||
|
||||
function hasCharacter(characterName) {
|
||||
|
|
24
Output.js
24
Output.js
|
@ -173,6 +173,20 @@ const modifier = (text) => {
|
|||
}
|
||||
text += "******************\n\n"
|
||||
break
|
||||
case "locations":
|
||||
text += `Player location: ${state.location == null ? "" : state.location + " "}(${state.x},${state.y})\n`
|
||||
text += `*** LOCATIONS ***\n`
|
||||
if (state.locations.length > 0) {
|
||||
var index = 0
|
||||
state.locations.forEach(function(location) {
|
||||
var distance = pointDistance(state.x, state.y, location.x, location.y).toFixed(1)
|
||||
text += `${++index}. ${toTitleCase(location.name)} (${location.x},${location.y}) Distance: ${distance}\n`
|
||||
})
|
||||
} else {
|
||||
text += `No locations have been discovered!`
|
||||
}
|
||||
text += "******************\n\n"
|
||||
break
|
||||
case "none":
|
||||
text += " "
|
||||
break
|
||||
|
@ -305,6 +319,16 @@ const modifier = (text) => {
|
|||
text += "\n#spellbook"
|
||||
text += "\n Shows the list of spells that the character has learned."
|
||||
|
||||
text += "\n\n--Locations--"
|
||||
text += "\n#createlocation (x) (y) location_name"
|
||||
text += "\n Creates a location at the given coordinates. If the coordinates are not provided, they are randomized within a range of 10 units from the player's current location. Multiple locations may exist at the same coordinates. A story card is created for the location. Quotes are not necessary."
|
||||
text += "\n#goto (x) (y) or (location_name)"
|
||||
text += "\n Makes the characters travel to the location specified by the coordinates or location_name. You must provide at least one or the other. If the location does not exist, it is created at your current coordinates. If you only specify coordinates, you will go to the first location at those coordinates. Quotes are not necessary."
|
||||
text += "\n#getlocation"
|
||||
text += "\n Returns the coordinates that the player's party is at. It will also list a location if a location was specified when using #goto."
|
||||
text += "\n#removelocation location_name or location_number"
|
||||
text += "\n Removes the specified location or location number as listed in #showlocations. Quotes are not necessary."
|
||||
|
||||
text += "\n\n--Danger Zone--"
|
||||
text += "\n#reset"
|
||||
text += "\n Removes all characters and changes all settings to their defaults. Use with caution!"
|
||||
|
|
|
@ -15,6 +15,7 @@ Personalized note system that does not take up context space<br>
|
|||
See the [user guide here](https://github.com/raeleus/Hashtag-DnD/wiki).
|
||||
|
||||
v. 0.1.0
|
||||
* Added `#createlocation`, `#goto`, `#removelocation`, `#clearlocations`, `#getlocation` and `#showlocations` to enable travelling.
|
||||
* Added `#renameitem` to rename an existing item
|
||||
* Added `#renamecharacter` to rename an existing character
|
||||
* Added `#clonecharacter` to copy an existing character
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue