initial commit
This commit is contained in:
commit
0c123ddeac
14
zz_meta/bases/PDFinfo.base
Normal file
14
zz_meta/bases/PDFinfo.base
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
filters:
|
||||||
|
and:
|
||||||
|
- this.pdfs.contains(file)
|
||||||
|
formulas:
|
||||||
|
File Size: if(file.size > 1024*1024, ((file.size / 1024 / 1024).toFixed(2) + "m"), if(file.size > 1024, ((file.size / 1024).toFixed(2) + "k"), file.size))
|
||||||
|
views:
|
||||||
|
- type: table
|
||||||
|
name: PDF List
|
||||||
|
order:
|
||||||
|
- file.name
|
||||||
|
- formula.File Size
|
||||||
|
sort:
|
||||||
|
- property: file.name
|
||||||
|
direction: ASC
|
||||||
126
zz_meta/bases/ttrpg/CampaignInfo.base
Normal file
126
zz_meta/bases/ttrpg/CampaignInfo.base
Normal file
@ -0,0 +1,126 @@
|
|||||||
|
filters:
|
||||||
|
or:
|
||||||
|
- and:
|
||||||
|
- list(campaigns).contains(this)
|
||||||
|
- this.hasTag("ttrpg/campaign")
|
||||||
|
- list(this.campaigns).filter(list(campaigns).contains(value)).length > 0
|
||||||
|
formulas:
|
||||||
|
Note: file.asLink(if(note.title, note.title, file.basename))
|
||||||
|
Game Date: '[note["fc-date"], note["fc-end"]].filter(value).join(" – ")'
|
||||||
|
Real Date: '"" + realDate'
|
||||||
|
Place Type: if(file.hasTag("ttrpg/place/poi"), "Point of Interest", if(file.hasTag("ttrpg/place/region"), "Region", if(file.hasTag("ttrpg/place/settlement"), "Settlement", "Unknown")))
|
||||||
|
Place Subtype: if(poiType, poiType, if(settlementType, settlementType, if(regionType, regionType)))
|
||||||
|
properties:
|
||||||
|
note.sessionNumber:
|
||||||
|
displayName: Num
|
||||||
|
note.summary:
|
||||||
|
displayName: Summary
|
||||||
|
note.realDate:
|
||||||
|
displayName: Date
|
||||||
|
note.ancestry:
|
||||||
|
displayName: Ancestry
|
||||||
|
note.pronouns:
|
||||||
|
displayName: Pronouns
|
||||||
|
note.languages:
|
||||||
|
displayName: Languages
|
||||||
|
note.factionType:
|
||||||
|
displayName: Type
|
||||||
|
note.leader:
|
||||||
|
displayName: Leader
|
||||||
|
note.itemType:
|
||||||
|
displayName: Item Type
|
||||||
|
views:
|
||||||
|
- type: cards
|
||||||
|
name: Player Character Cards
|
||||||
|
filters:
|
||||||
|
and:
|
||||||
|
- file.hasTag("ttrpg/person")
|
||||||
|
- personType == "pc"
|
||||||
|
order:
|
||||||
|
- formula.Note
|
||||||
|
- Player
|
||||||
|
- ancestry
|
||||||
|
- pronouns
|
||||||
|
image: note.image
|
||||||
|
- type: table
|
||||||
|
name: Sessions
|
||||||
|
filters:
|
||||||
|
and:
|
||||||
|
- file.hasTag("ttrpg/session")
|
||||||
|
order:
|
||||||
|
- formula.Note
|
||||||
|
- sessionNumber
|
||||||
|
- formula.Real Date
|
||||||
|
- formula.Game Date
|
||||||
|
- summary
|
||||||
|
sort:
|
||||||
|
- property: sessionNumber
|
||||||
|
direction: ASC
|
||||||
|
- type: table
|
||||||
|
name: Factions
|
||||||
|
filters:
|
||||||
|
and:
|
||||||
|
- file.hasTag("ttrpg/faction")
|
||||||
|
order:
|
||||||
|
- formula.Note
|
||||||
|
- factionType
|
||||||
|
- leader
|
||||||
|
- summary
|
||||||
|
sort:
|
||||||
|
- property: formula.Note
|
||||||
|
direction: ASC
|
||||||
|
columnSize:
|
||||||
|
formula.Note: 125
|
||||||
|
note.factionType: 102
|
||||||
|
- type: table
|
||||||
|
name: Nonplayer Characters
|
||||||
|
filters:
|
||||||
|
and:
|
||||||
|
- file.hasTag("ttrpg/person")
|
||||||
|
- personType != "pc"
|
||||||
|
order:
|
||||||
|
- formula.Note
|
||||||
|
- ancestry
|
||||||
|
- pronouns
|
||||||
|
- languages
|
||||||
|
- summary
|
||||||
|
columnSize:
|
||||||
|
formula.Note: 140
|
||||||
|
note.pronouns: 111
|
||||||
|
note.languages: 127
|
||||||
|
- type: table
|
||||||
|
name: Places
|
||||||
|
filters:
|
||||||
|
and:
|
||||||
|
- file.hasTag("ttrpg/place")
|
||||||
|
groupBy:
|
||||||
|
property: formula.Place Type
|
||||||
|
direction: ASC
|
||||||
|
order:
|
||||||
|
- formula.Note
|
||||||
|
- formula.Place Type
|
||||||
|
- formula.Place Subtype
|
||||||
|
- location
|
||||||
|
- summary
|
||||||
|
sort:
|
||||||
|
- property: formula.Note
|
||||||
|
direction: ASC
|
||||||
|
- property: location
|
||||||
|
direction: ASC
|
||||||
|
columnSize:
|
||||||
|
formula.Note: 86
|
||||||
|
formula.Place Type: 114
|
||||||
|
note.location: 107
|
||||||
|
note.summary: 134
|
||||||
|
formula.Place Subtype: 130
|
||||||
|
- type: table
|
||||||
|
name: Items
|
||||||
|
filters:
|
||||||
|
and:
|
||||||
|
- file.hasTag("ttrpg/item")
|
||||||
|
order:
|
||||||
|
- formula.Note
|
||||||
|
- itemType
|
||||||
|
- summary
|
||||||
|
columnSize:
|
||||||
|
note.itemType: 136
|
||||||
43
zz_meta/bases/ttrpg/FactionInfo.base
Normal file
43
zz_meta/bases/ttrpg/FactionInfo.base
Normal file
@ -0,0 +1,43 @@
|
|||||||
|
formulas:
|
||||||
|
Type: if(file.hasTag("ttrpg/faction"), "Faction (" + note.factionType + ")", if(file.hasTag("ttrpg/person"), "Person (" + note.personType + ")", "Other"))
|
||||||
|
Category: |-
|
||||||
|
if(
|
||||||
|
file.hasTag("ttrpg/faction"),
|
||||||
|
"Faction (" + factionType + ")",
|
||||||
|
if(
|
||||||
|
file.hasTag("ttrpg/person"),
|
||||||
|
"Person (" + personType + ")", "Unknown"
|
||||||
|
)
|
||||||
|
)
|
||||||
|
Note: file.asLink(if(note.title, note.title, file.basename))
|
||||||
|
properties:
|
||||||
|
note.summary:
|
||||||
|
displayName: Summary
|
||||||
|
views:
|
||||||
|
- type: table
|
||||||
|
name: Members
|
||||||
|
filters:
|
||||||
|
and:
|
||||||
|
- or:
|
||||||
|
- |-
|
||||||
|
list(factions).filter(
|
||||||
|
list(file(value).properties.factions)
|
||||||
|
.contains(this)
|
||||||
|
).length > 0
|
||||||
|
- list(factions).contains(this)
|
||||||
|
- list(this.leader).contains(file)
|
||||||
|
- or:
|
||||||
|
- file.hasTag("ttrpg/faction")
|
||||||
|
- file.hasTag("ttrpg/person")
|
||||||
|
order:
|
||||||
|
- formula.Note
|
||||||
|
- formula.Category
|
||||||
|
- summary
|
||||||
|
sort:
|
||||||
|
- property: file.name
|
||||||
|
direction: ASC
|
||||||
|
- property: formula.Category
|
||||||
|
direction: ASC
|
||||||
|
columnSize:
|
||||||
|
formula.Note: 151
|
||||||
|
formula.Category: 179
|
||||||
27
zz_meta/bases/ttrpg/RegionInfo.base
Normal file
27
zz_meta/bases/ttrpg/RegionInfo.base
Normal file
@ -0,0 +1,27 @@
|
|||||||
|
formulas:
|
||||||
|
Note: link(file,if(title,title,file.basename))
|
||||||
|
Place Type: if(file.hasTag("ttrpg/place/region"),"Region", if(file.hasTag("ttrpg/place/settlement"), "Settlement", "Point of Interest"))
|
||||||
|
Place Subtype: if(regionType, regionType, if(settlementType, settlementType, poiType))
|
||||||
|
views:
|
||||||
|
- type: table
|
||||||
|
name: Places
|
||||||
|
filters:
|
||||||
|
and:
|
||||||
|
- file.hasTag("ttrpg/place")
|
||||||
|
- or:
|
||||||
|
- |-
|
||||||
|
list(location).filter(
|
||||||
|
list(file(value).properties.location)
|
||||||
|
.contains(this) && file(value).hasTag("ttrpg/place/region")
|
||||||
|
).length > 0
|
||||||
|
- list(location).contains(this.file)
|
||||||
|
order:
|
||||||
|
- formula.Note
|
||||||
|
- formula.Place Type
|
||||||
|
- formula.Place Subtype
|
||||||
|
- summary
|
||||||
|
sort:
|
||||||
|
- property: file.name
|
||||||
|
direction: DESC
|
||||||
|
columnSize:
|
||||||
|
formula.Note: 135
|
||||||
23
zz_meta/bases/ttrpg/SessionInfo.base
Normal file
23
zz_meta/bases/ttrpg/SessionInfo.base
Normal file
@ -0,0 +1,23 @@
|
|||||||
|
filters:
|
||||||
|
and:
|
||||||
|
- list(this.campaigns).containsAny(list(campaigns))
|
||||||
|
- file.hasTag("ttrpg/session")
|
||||||
|
formulas:
|
||||||
|
Session: sessionNumber
|
||||||
|
Title: if(title, title, file.basename)
|
||||||
|
properties:
|
||||||
|
formula.Session:
|
||||||
|
displayName: Session Number
|
||||||
|
views:
|
||||||
|
- type: cards
|
||||||
|
name: Navigation
|
||||||
|
filters:
|
||||||
|
or:
|
||||||
|
- (sessionNUmber - this.sessionNumber).abs() == 1
|
||||||
|
order:
|
||||||
|
- formula.Title
|
||||||
|
- summary
|
||||||
|
sort:
|
||||||
|
- property: sessionNumber
|
||||||
|
direction: ASC
|
||||||
|
cardSize: 340
|
||||||
59
zz_meta/bases/ttrpg/SettlementInfo.base
Normal file
59
zz_meta/bases/ttrpg/SettlementInfo.base
Normal file
@ -0,0 +1,59 @@
|
|||||||
|
formulas:
|
||||||
|
Note: link(file, if(title, title, file.basename))
|
||||||
|
Place Type: if(file.hasTag("ttrpg/place/region"),"Region", if(file.hasTag("ttrpg/place/settlement"), "Settlement", "Point of Interest"))
|
||||||
|
Place Subtype: if(regionType, regionType, if(settlementType, settlementType, poiType))
|
||||||
|
views:
|
||||||
|
- type: table
|
||||||
|
name: Places
|
||||||
|
filters:
|
||||||
|
and:
|
||||||
|
- file.hasTag("ttrpg/place")
|
||||||
|
- or:
|
||||||
|
- |-
|
||||||
|
list(location).filter(
|
||||||
|
list(file(value).properties.location)
|
||||||
|
.contains(this)
|
||||||
|
).length > 0
|
||||||
|
- list(location).contains(this.file)
|
||||||
|
order:
|
||||||
|
- formula.Note
|
||||||
|
- formula.Place Type
|
||||||
|
- formula.Place Subtype
|
||||||
|
- summary
|
||||||
|
sort:
|
||||||
|
- property: file.name
|
||||||
|
direction: DESC
|
||||||
|
columnSize:
|
||||||
|
formula.Note: 135
|
||||||
|
- type: table
|
||||||
|
name: People
|
||||||
|
filters:
|
||||||
|
and:
|
||||||
|
- or:
|
||||||
|
- list(this.residents).contains(file)
|
||||||
|
- list(this.leader).contains(file)
|
||||||
|
- |-
|
||||||
|
list(this.leader).filter(
|
||||||
|
list(file.properties.factions)
|
||||||
|
.contains(value)
|
||||||
|
).length > 0
|
||||||
|
- |-
|
||||||
|
list(this.residents).filter(
|
||||||
|
list(file.properties.factions)
|
||||||
|
.contains(value)
|
||||||
|
).length > 0
|
||||||
|
- |-
|
||||||
|
list(location).filter(
|
||||||
|
list(file(value).properties.location)
|
||||||
|
.contains(this)
|
||||||
|
).length > 0
|
||||||
|
- list(location).contains(this)
|
||||||
|
- or:
|
||||||
|
- file.hasTag("ttrpg/person")
|
||||||
|
order:
|
||||||
|
- formula.Note
|
||||||
|
- pronunciation
|
||||||
|
- pronouns
|
||||||
|
- summary
|
||||||
|
columnSize:
|
||||||
|
formula.Note: 149
|
||||||
13
zz_meta/bases/ttrpg/SystemInfo.base
Normal file
13
zz_meta/bases/ttrpg/SystemInfo.base
Normal file
@ -0,0 +1,13 @@
|
|||||||
|
filters:
|
||||||
|
and:
|
||||||
|
- link(system).asFile() == this.file
|
||||||
|
formulas:
|
||||||
|
Note: file.asLink(if(title, title, file.basename))
|
||||||
|
views:
|
||||||
|
- type: list
|
||||||
|
name: Rules Helpers
|
||||||
|
filters:
|
||||||
|
and:
|
||||||
|
- file.hasTag("ttrpg/rules")
|
||||||
|
order:
|
||||||
|
- formula.Note
|
||||||
33
zz_meta/bases/ttrpg/SystemSettingCampaigns.base
Normal file
33
zz_meta/bases/ttrpg/SystemSettingCampaigns.base
Normal file
@ -0,0 +1,33 @@
|
|||||||
|
filters:
|
||||||
|
and:
|
||||||
|
- or:
|
||||||
|
- and:
|
||||||
|
- this.file.hasTag("ttrpg/setting")
|
||||||
|
- link(setting).asFile() == this.file
|
||||||
|
- and:
|
||||||
|
- this.file.hasTag("ttrpg/system")
|
||||||
|
- link(system).asFile() == this.file
|
||||||
|
- file.hasTag("ttrpg/campaign")
|
||||||
|
formulas:
|
||||||
|
Players: players.join(", ")
|
||||||
|
properties:
|
||||||
|
note.players:
|
||||||
|
displayName: Players
|
||||||
|
note.system:
|
||||||
|
displayName: System
|
||||||
|
note.gm:
|
||||||
|
displayName: GM
|
||||||
|
note.setting:
|
||||||
|
displayName: Setting
|
||||||
|
views:
|
||||||
|
- type: cards
|
||||||
|
name: Campaigns
|
||||||
|
order:
|
||||||
|
- file.name
|
||||||
|
- gm
|
||||||
|
- formula.Players
|
||||||
|
- system
|
||||||
|
- setting
|
||||||
|
cardSize: 200
|
||||||
|
imageAspectRatio: 0.65
|
||||||
|
image: note.image
|
||||||
85
zz_meta/js/templater/ttrpg.js
Normal file
85
zz_meta/js/templater/ttrpg.js
Normal file
@ -0,0 +1,85 @@
|
|||||||
|
function fileHasTag(file, tag) {
|
||||||
|
const cache = app.metadataCache.getFileCache(file);
|
||||||
|
const allTags = (cache?.frontmatter?.tags ?? []).concat(
|
||||||
|
cache?.tags?.map((t) => (t.tag[0] === "#" ? t.tag.slice(1) : t.tag)),
|
||||||
|
);
|
||||||
|
return allTags.some((t) => t === tag || t?.startsWith(`${tag}/`));
|
||||||
|
}
|
||||||
|
|
||||||
|
function fileInParentWithTag(file, tag) {
|
||||||
|
return app.vault
|
||||||
|
.getMarkdownFiles()
|
||||||
|
.filter(
|
||||||
|
(mdFile) =>
|
||||||
|
file.path.startsWith(mdFile.parent.path) && fileHasTag(mdFile, tag),
|
||||||
|
)?.[0];
|
||||||
|
}
|
||||||
|
|
||||||
|
function campaignData(file) {
|
||||||
|
const campaignFile =
|
||||||
|
fileInParentWithTag(file, "ttrpg/campaign") ||
|
||||||
|
app.vault.getFileByPath("index.md");
|
||||||
|
const data = {};
|
||||||
|
console.log("campaign file", campaignFile);
|
||||||
|
if (campaignFile) {
|
||||||
|
const cache = app.metadataCache.getFileCache(campaignFile);
|
||||||
|
const fm = cache?.frontmatter;
|
||||||
|
const settingFile = frontmatterLinksToTFiles(campaignFile, "setting")?.[0];
|
||||||
|
data.players = fm?.players;
|
||||||
|
data.gm = fm?.gm;
|
||||||
|
data.title = fm?.title || campaignFile.basename;
|
||||||
|
data.system = fm?.system;
|
||||||
|
data.setting = fm?.setting;
|
||||||
|
data.settingFile = settingFile;
|
||||||
|
data.file = campaignFile;
|
||||||
|
data.link = app.fileManager.generateMarkdownLink(
|
||||||
|
campaignFile,
|
||||||
|
file.path,
|
||||||
|
null,
|
||||||
|
data.title,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
return data;
|
||||||
|
}
|
||||||
|
|
||||||
|
function frontmatterLinksToTFiles(sourceFile, property) {
|
||||||
|
const links = app.metadataCache.getFileCache(sourceFile)?.frontmatterLinks;
|
||||||
|
if (links) {
|
||||||
|
return app.metadataCache
|
||||||
|
.getFileCache(sourceFile)
|
||||||
|
?.frontmatterLinks?.filter((l) => l.key.startsWith(property))
|
||||||
|
?.map((l) =>
|
||||||
|
app.metadataCache.getFirstLinkpathDest(l.link, sourceFile.path),
|
||||||
|
)
|
||||||
|
?.filter((f) => f);
|
||||||
|
} else {
|
||||||
|
return [];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function settingData(file) {
|
||||||
|
const settingFile =
|
||||||
|
fileInParentWithTag(file, "ttrpg/setting") ||
|
||||||
|
campaignData(file)?.settingFile ||
|
||||||
|
app.vault.getFileByPath("index.md");
|
||||||
|
const data = {};
|
||||||
|
if (settingFile) {
|
||||||
|
const cache = app.metadataCache.getFileCache(settingFile);
|
||||||
|
const fm = cache?.frontmatter;
|
||||||
|
data.title = fm?.title || campaignFile.basename;
|
||||||
|
data.file = settingFile;
|
||||||
|
data.calendar = fm?.["fc-calendar"];
|
||||||
|
data.link = app.fileManager.generateMarkdownLink(
|
||||||
|
settingFile,
|
||||||
|
file.path,
|
||||||
|
null,
|
||||||
|
data.title,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
return data;
|
||||||
|
}
|
||||||
|
|
||||||
|
module.exports = {
|
||||||
|
campaignData: campaignData,
|
||||||
|
settingData: settingData,
|
||||||
|
};
|
||||||
113
zz_meta/js/templater/util.js
Normal file
113
zz_meta/js/templater/util.js
Normal file
@ -0,0 +1,113 @@
|
|||||||
|
async function updateMetadata(tp, options) {
|
||||||
|
console.log("options", options);
|
||||||
|
const file = tp.config.target_file;
|
||||||
|
const data = options?.data ?? {};
|
||||||
|
const tags = new Set([options?.tags ?? []].flat());
|
||||||
|
const tagsToRemove = new Set([options?.tagsToRemove ?? []].flat());
|
||||||
|
const title = options?.title;
|
||||||
|
for (const tag of tags) {
|
||||||
|
const splitTag = tag.split("/");
|
||||||
|
for (let i = 1; i < splitTag.length; i++) {
|
||||||
|
tagsToRemove.add(splitTag.slice(0, i).join("/"));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (tp.file.title === "Untitled" && title) {
|
||||||
|
await tp.file.rename(title);
|
||||||
|
}
|
||||||
|
tp.hooks.on_all_templates_executed(async () => {
|
||||||
|
await tp.app.fileManager.processFrontMatter(file, (frontmatter) => {
|
||||||
|
console.log("frontmatter before", frontmatter);
|
||||||
|
let fmTags = new Set([frontmatter.tags ?? []].flat());
|
||||||
|
fmTags = tags.difference(tagsToRemove).union(tags);
|
||||||
|
frontmatter.tags = Array.from(fmTags);
|
||||||
|
frontmatter.tags.sort();
|
||||||
|
for (const key in data) {
|
||||||
|
frontmatter[key] = data[key];
|
||||||
|
}
|
||||||
|
console.log("frontmatter before", frontmatter);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
function getFileProperty(file, property) {
|
||||||
|
const frontmatter = app.metadataCache.getFileCache(file)?.frontmatter;
|
||||||
|
return frontmatter?.[property];
|
||||||
|
}
|
||||||
|
|
||||||
|
function hasPropertyValue(file, property, value) {
|
||||||
|
const propValue = getFileProperty(file, property);
|
||||||
|
if (Array.isArray(propValue)) {
|
||||||
|
return propValue.includes(value);
|
||||||
|
}
|
||||||
|
|
||||||
|
return propValue === value;
|
||||||
|
}
|
||||||
|
|
||||||
|
function frontmatterLinksToTFiles(sourceFile, property) {
|
||||||
|
const links = app.metadataCache.getFileCache(sourceFile)?.frontmatterLinks;
|
||||||
|
if (links) {
|
||||||
|
return app.metadataCache
|
||||||
|
.getFileCache(sourceFile)
|
||||||
|
?.frontmatterLinks?.filter((l) => l.key.startsWith(property))
|
||||||
|
?.map((l) =>
|
||||||
|
app.metadataCache.getFirstLinkpathDest(l.link, sourceFile.path),
|
||||||
|
)
|
||||||
|
?.filter((f) => f);
|
||||||
|
} else {
|
||||||
|
return [];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function slugify(input) {
|
||||||
|
if (!input) return "";
|
||||||
|
|
||||||
|
// Make lower case and trim
|
||||||
|
var slug = input.toLowerCase().trim();
|
||||||
|
|
||||||
|
// Remove accents from characters
|
||||||
|
slug = slug.normalize("NFD").replace(/[\u0300-\u036f]/g, "");
|
||||||
|
|
||||||
|
// Replace invalid chars with spaces
|
||||||
|
slug = slug.replace(/[^a-z0-9\s-]/g, " ").trim();
|
||||||
|
|
||||||
|
// Replace multiple spaces or hyphens with a single hyphen
|
||||||
|
slug = slug.replace(/[\s-]+/g, "-");
|
||||||
|
|
||||||
|
return slug;
|
||||||
|
}
|
||||||
|
|
||||||
|
function getAllTags(file) {
|
||||||
|
const cache = app.metadataCache.getFileCache(file);
|
||||||
|
const fileTags =
|
||||||
|
cache?.tags?.map((t) => (t.tag[0] === "#" ? t.tag.slice(1) : t.tag)) || [];
|
||||||
|
const fmTags = [cache?.frontmatter?.tags || []].flat();
|
||||||
|
return fmTags.concat(fileTags);
|
||||||
|
}
|
||||||
|
|
||||||
|
function filesWithTag(tag) {
|
||||||
|
console.log("files with tag", tag);
|
||||||
|
const files = app.vault.getMarkdownFiles().filter((file) => {
|
||||||
|
const tags = getAllTags(file);
|
||||||
|
return tags?.includes(tag) || tags?.some((t) => t.startsWith(`${tag}/`));
|
||||||
|
});
|
||||||
|
return files;
|
||||||
|
}
|
||||||
|
|
||||||
|
function fileHasTag(file, tag) {
|
||||||
|
const cache = app.metadataCache.getFileCache(file);
|
||||||
|
const allTags = (cache?.frontmatter?.tags ?? []).concat(
|
||||||
|
cache?.tags?.map((t) => (t.tag[0] === "#" ? t.tag.slice(1) : t.tag)),
|
||||||
|
);
|
||||||
|
return allTags.some((t) => t === tag || t?.startsWith(`${tag}/`));
|
||||||
|
}
|
||||||
|
|
||||||
|
module.exports = {
|
||||||
|
slugify,
|
||||||
|
getAllTags,
|
||||||
|
filesWithTag,
|
||||||
|
fileHasTag,
|
||||||
|
frontmatterLinksToTFiles,
|
||||||
|
getFileProperty,
|
||||||
|
hasPropertyValue,
|
||||||
|
updateMetadata,
|
||||||
|
};
|
||||||
16
zz_meta/shell/ttrpg/update_faction_metadata.sh
Executable file
16
zz_meta/shell/ttrpg/update_faction_metadata.sh
Executable file
@ -0,0 +1,16 @@
|
|||||||
|
#!/bin/zsh
|
||||||
|
for file in **/*.md; do
|
||||||
|
echo "foo$file"
|
||||||
|
yq \
|
||||||
|
--front-matter="process" \
|
||||||
|
--inplace \
|
||||||
|
'
|
||||||
|
.tags = ["ttrpg/faction"] |
|
||||||
|
.icon = "users" |
|
||||||
|
.summary = .summary // "" |
|
||||||
|
.campaigns = ["[[Kingmaker|Kingmaker]]"] |
|
||||||
|
del(.type) |
|
||||||
|
del(.campaign)
|
||||||
|
' \
|
||||||
|
"${file}"
|
||||||
|
done
|
||||||
31
zz_meta/shell/ttrpg/update_session_metadata.sh
Executable file
31
zz_meta/shell/ttrpg/update_session_metadata.sh
Executable file
@ -0,0 +1,31 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
files=Session*.md
|
||||||
|
for file in ${files[@]}; do
|
||||||
|
echo "$file"
|
||||||
|
export realDate=$(grep 'Real World Date' "$file" | cut -d' ' -f5)
|
||||||
|
yq \
|
||||||
|
--front-matter="process" \
|
||||||
|
--inplace \
|
||||||
|
'
|
||||||
|
.tags = ["ttrpg/session"] |
|
||||||
|
.icon = "book-open" |
|
||||||
|
.title = "Session " + .session_number |
|
||||||
|
.gm = "Mike" |
|
||||||
|
.players = ["Jeff", "Brian", "Oz", "Andy", "Oz"] |
|
||||||
|
.sessionNumber = .session_number |
|
||||||
|
.summary = .summary // .["aat-event-body"] // "" |
|
||||||
|
.aliases = ["Session " + .session_number] |
|
||||||
|
.realDate = strenv(realDate) |
|
||||||
|
.["fc-calendar"] = "Calendar of Golarion" |
|
||||||
|
.["fc-display-name"] = "Kingmaker Session " + .session_number |
|
||||||
|
.["fc-category"] = "Kingmaker" |
|
||||||
|
.campaigns = ["[[Kingmaker|Kingmaker]]"] |
|
||||||
|
del(.type) |
|
||||||
|
del(.timelines) |
|
||||||
|
del(.["aat-render-enabled"]) |
|
||||||
|
del(.session_number) |
|
||||||
|
del(.campaign) |
|
||||||
|
del(.["aat-event-body"])
|
||||||
|
' \
|
||||||
|
"${file}"
|
||||||
|
done
|
||||||
78
zz_meta/templater/ttrpg/campaign.md
Normal file
78
zz_meta/templater/ttrpg/campaign.md
Normal file
@ -0,0 +1,78 @@
|
|||||||
|
<%*
|
||||||
|
const title = (
|
||||||
|
tp.file.title === "Untitled"
|
||||||
|
? await tp.system.prompt("Campaign Title")
|
||||||
|
: tp.file.title
|
||||||
|
);
|
||||||
|
const gm = await tp.system.prompt("Add a GM to this campaign")
|
||||||
|
let isAddingPlayers = true;
|
||||||
|
const players = [];
|
||||||
|
while (isAddingPlayers) {
|
||||||
|
const player = await tp.system.prompt("Add a player to this campaign")
|
||||||
|
if (player) {
|
||||||
|
players.push(player)
|
||||||
|
} else {
|
||||||
|
isAddingPlayers = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
const settingFiles = tp.user.util.filesWithTag("ttrpg/setting");
|
||||||
|
const settingFile = (
|
||||||
|
settingFiles.length > 0
|
||||||
|
? await tp.system.suggester((file) => file.basename, settingFiles, false, "Select a setting")
|
||||||
|
: null
|
||||||
|
);
|
||||||
|
const systemFiles = tp.user.util.filesWithTag("ttrpg/system");
|
||||||
|
const systemFile = (
|
||||||
|
systemFiles.length > 0
|
||||||
|
? await tp.system.suggester((file) => file.basename, systemFiles, false, "Select a system")
|
||||||
|
: null
|
||||||
|
);
|
||||||
|
const metadata = {
|
||||||
|
title,
|
||||||
|
tags: ["ttrpg/campaign"],
|
||||||
|
data: {
|
||||||
|
icon: "notebook-tabs",
|
||||||
|
title,
|
||||||
|
players,
|
||||||
|
gm,
|
||||||
|
pdfs: [],
|
||||||
|
campaignStatus: "planning",
|
||||||
|
},
|
||||||
|
};
|
||||||
|
if (settingFile) {
|
||||||
|
metadata.data.setting = tp.app.fileManager.generateMarkdownLink(
|
||||||
|
settingFile, tp.file.path(true), null, settingFile.basename
|
||||||
|
);
|
||||||
|
}
|
||||||
|
if (systemFile) {
|
||||||
|
metadata.data.system = tp.app.fileManager.generateMarkdownLink(
|
||||||
|
systemFile, tp.file.path(true), null, systemFile.basename
|
||||||
|
);
|
||||||
|
}
|
||||||
|
await tp.user.util.updateMetadata(tp, metadata);
|
||||||
|
%>
|
||||||
|
|
||||||
|
<% tp.file.cursor() %>
|
||||||
|
|
||||||
|
## Player Characters
|
||||||
|
|
||||||
|
![[CampaignInfo.base#Player Character Cards]]
|
||||||
|
## Sessions
|
||||||
|
|
||||||
|
![[CampaignInfo.base#Sessions]]
|
||||||
|
|
||||||
|
## Factions
|
||||||
|
|
||||||
|
![[CampaignInfo.base#Factions]]
|
||||||
|
|
||||||
|
## NPCs
|
||||||
|
|
||||||
|
![[CampaignInfo.base#Nonplayer Characters]]
|
||||||
|
|
||||||
|
## Places
|
||||||
|
|
||||||
|
![[CampaignInfo.base#Places]]
|
||||||
|
|
||||||
|
## PDFs
|
||||||
|
|
||||||
|
![[PDFinfo.base]]
|
||||||
28
zz_meta/templater/ttrpg/creature.md
Normal file
28
zz_meta/templater/ttrpg/creature.md
Normal file
@ -0,0 +1,28 @@
|
|||||||
|
<%*
|
||||||
|
const thisFile = tp.config.target_file;
|
||||||
|
const campaignData = tp.user.ttrpg.campaignData(thisFile)
|
||||||
|
const settingData = tp.user.ttrpg.settingData(thisFile);
|
||||||
|
const title = tp.file.title === "Untitled"
|
||||||
|
? await tp.system.prompt("Creature Name")
|
||||||
|
: tp.file.title;
|
||||||
|
|
||||||
|
const type = tp.frontmatter.creatureType ?? ""
|
||||||
|
const metadata = {
|
||||||
|
tags: ['ttrpg/creature'],
|
||||||
|
data: {
|
||||||
|
icon: "squirrel",
|
||||||
|
title,
|
||||||
|
pronunciation: tp.frontmatter.pronunciation ?? "",
|
||||||
|
summary: tp.frontmatter?.summary ?? "",
|
||||||
|
campaigns: [campaignData.link],
|
||||||
|
setting: settingData.link,
|
||||||
|
system: tp.frontmatter?.system ?? "",
|
||||||
|
creatureType: type,
|
||||||
|
adjective: tp.frontmatter?.adjective ?? "",
|
||||||
|
},
|
||||||
|
title,
|
||||||
|
};
|
||||||
|
await tp.user.util.updateMetadata(tp, metadata);
|
||||||
|
%>
|
||||||
|
|
||||||
|
<% tp.file.cursor() %>
|
||||||
44
zz_meta/templater/ttrpg/faction.md
Normal file
44
zz_meta/templater/ttrpg/faction.md
Normal file
@ -0,0 +1,44 @@
|
|||||||
|
<%*
|
||||||
|
const thisFile = tp.config.target_file;
|
||||||
|
const campaignData = tp.user.ttrpg.campaignData(thisFile)
|
||||||
|
const settingData = tp.user.ttrpg.settingData(thisFile);
|
||||||
|
const title = tp.file.title === "Untitled"
|
||||||
|
? await tp.system.prompt("Faction Name")
|
||||||
|
: tp.file.title;
|
||||||
|
const adjective = tp.frontmatter?.adjective ?? "";
|
||||||
|
const types = [
|
||||||
|
"family",
|
||||||
|
"military",
|
||||||
|
"secret society",
|
||||||
|
"political",
|
||||||
|
"government",
|
||||||
|
"religious",
|
||||||
|
"academic",
|
||||||
|
"criminal",
|
||||||
|
"social",
|
||||||
|
"commercial",
|
||||||
|
"ethnic group",
|
||||||
|
];
|
||||||
|
const type = tp.frontmatter.factionType ?? await tp.system.suggester(v => v, types, true, "Type of Faction");
|
||||||
|
const metadata = {
|
||||||
|
tags: ['ttrpg/faction'],
|
||||||
|
data: {
|
||||||
|
icon: "users",
|
||||||
|
title,
|
||||||
|
pronunciation: tp.frontmatter.pronunciation ?? "",
|
||||||
|
summary: tp.frontmatter?.summary ?? "",
|
||||||
|
campaigns: [campaignData.link],
|
||||||
|
setting: settingData.link,
|
||||||
|
factionType: type,
|
||||||
|
headquarters: tp.frontmatter?.headquarters ?? "",
|
||||||
|
leader: tp.frontmatter?.leader ?? "",
|
||||||
|
adjective: tp.frontmatter?.adjective ?? "",
|
||||||
|
},
|
||||||
|
title,
|
||||||
|
};
|
||||||
|
await tp.user.util.updateMetadata(tp, metadata);
|
||||||
|
%>
|
||||||
|
<% tp.file.cursor() %>
|
||||||
|
## Members
|
||||||
|
![[FactionInfo.base#Members]]
|
||||||
|
|
||||||
27
zz_meta/templater/ttrpg/item.md
Normal file
27
zz_meta/templater/ttrpg/item.md
Normal file
@ -0,0 +1,27 @@
|
|||||||
|
<%*
|
||||||
|
const thisFile = tp.config.target_file;
|
||||||
|
const campaignData = tp.user.ttrpg.campaignData(thisFile)
|
||||||
|
const settingData = tp.user.ttrpg.settingData(thisFile);
|
||||||
|
const title = tp.file.title === "Untitled"
|
||||||
|
? await tp.system.prompt("Item Name")
|
||||||
|
: tp.file.title;
|
||||||
|
|
||||||
|
const type = tp.frontmatter.itemType ?? ""
|
||||||
|
const metadata = {
|
||||||
|
tags: ['ttrpg/item'],
|
||||||
|
data: {
|
||||||
|
icon: "amphora",
|
||||||
|
title,
|
||||||
|
pronunciation: tp.frontmatter.pronunciation ?? "",
|
||||||
|
summary: tp.frontmatter?.summary ?? "",
|
||||||
|
campaigns: [campaignData.link],
|
||||||
|
setting: settingData.link,
|
||||||
|
system: tp.frontmatter?.system ?? "",
|
||||||
|
itemType: type,
|
||||||
|
},
|
||||||
|
title,
|
||||||
|
};
|
||||||
|
await tp.user.util.updateMetadata(tp, metadata);
|
||||||
|
%>
|
||||||
|
|
||||||
|
<% tp.file.cursor() %>
|
||||||
43
zz_meta/templater/ttrpg/person.md
Normal file
43
zz_meta/templater/ttrpg/person.md
Normal file
@ -0,0 +1,43 @@
|
|||||||
|
<%*
|
||||||
|
const thisFile = tp.config.target_file;
|
||||||
|
const campaignData = tp.user.ttrpg.campaignData(thisFile)
|
||||||
|
const settingData = tp.user.ttrpg.settingData(thisFile);
|
||||||
|
const title = tp.file.title === "Untitled"
|
||||||
|
? await tp.system.prompt("Person Name")
|
||||||
|
: tp.file.title;
|
||||||
|
const genders = {
|
||||||
|
"N/A": "it",
|
||||||
|
"Male": "he/him",
|
||||||
|
"Female": "she/her",
|
||||||
|
"Nonbinary": "they/them",
|
||||||
|
}
|
||||||
|
const types = {"npc": "Non-player Character", "pc": "Player Character"};
|
||||||
|
const type = tp.frontmatter.personType ?? await tp.system.suggester(v => types[v], Object.keys(types), true, "Type of Character");
|
||||||
|
const gender = tp.frontmatter?.gender ?? (await tp.system.suggester(v => v, Object.keys(genders), false, "Gender") ?? "N/A");
|
||||||
|
const pronouns = tp.frontmatter.pronouns ?? genders[gender];
|
||||||
|
const metadata = {
|
||||||
|
tags: ['ttrpg/person'],
|
||||||
|
data: {
|
||||||
|
icon: "user",
|
||||||
|
title,
|
||||||
|
pronunciation: tp.frontmatter.pronunciation ?? "",
|
||||||
|
summary: tp.frontmatter?.summary ?? "",
|
||||||
|
campaigns: [campaignData.link],
|
||||||
|
setting: settingData.link,
|
||||||
|
personType: type,
|
||||||
|
gender,
|
||||||
|
pronouns,
|
||||||
|
ancestry: tp.frontmatter?.ancestry ?? "",
|
||||||
|
languages: tp.frontmatter?.languages ?? [],
|
||||||
|
factions: tp.frontmatter?.factions ?? [],
|
||||||
|
location: tp.frontmatter?.location ?? [],
|
||||||
|
},
|
||||||
|
title,
|
||||||
|
};
|
||||||
|
if (type === "pc") {
|
||||||
|
metadata.data.player = tp.frontmatter?.player ?? await tp.system.prompt("Player Name");
|
||||||
|
}
|
||||||
|
await tp.user.util.updateMetadata(tp, metadata);
|
||||||
|
%>
|
||||||
|
|
||||||
|
<% tp.file.cursor() %>
|
||||||
44
zz_meta/templater/ttrpg/point-of-interest.md
Normal file
44
zz_meta/templater/ttrpg/point-of-interest.md
Normal file
@ -0,0 +1,44 @@
|
|||||||
|
<%*
|
||||||
|
const thisFile = tp.config.target_file;
|
||||||
|
const campaignData = tp.user.ttrpg.campaignData(thisFile)
|
||||||
|
const settingData = tp.user.ttrpg.settingData(thisFile);
|
||||||
|
const title = tp.file.title === "Untitled"
|
||||||
|
? await tp.system.prompt("Location Name")
|
||||||
|
: tp.file.title;
|
||||||
|
const adjective = tp.frontmatter?.adjective ?? "";
|
||||||
|
const types = [
|
||||||
|
"shop",
|
||||||
|
"landmark",
|
||||||
|
"residence",
|
||||||
|
"temple",
|
||||||
|
"government building",
|
||||||
|
"factory",
|
||||||
|
"fortress",
|
||||||
|
"military building",
|
||||||
|
"ruin",
|
||||||
|
"cave",
|
||||||
|
"ship",
|
||||||
|
];
|
||||||
|
const type = tp.frontmatter.poiType ?? await tp.system.suggester(v => v, types, true, "Type of PoI");
|
||||||
|
const metadata = {
|
||||||
|
tags: ['ttrpg/place/poi'],
|
||||||
|
data: {
|
||||||
|
icon: "map-pin",
|
||||||
|
title,
|
||||||
|
pronunciation: tp.frontmatter.pronunciation ?? "",
|
||||||
|
summary: tp.frontmatter?.summary ?? "",
|
||||||
|
campaigns: [campaignData.link],
|
||||||
|
setting: settingData.link,
|
||||||
|
poiType: type,
|
||||||
|
location: tp.frontmatter?.location ?? "",
|
||||||
|
wares: tp.frontmatter?.wares ?? "",
|
||||||
|
proprietor: tp.frontmatter?.proprietor ?? "",
|
||||||
|
residents: tp.frontmatter?.residents ?? [],
|
||||||
|
factions: tp.frontmatter?.factions ?? [],
|
||||||
|
},
|
||||||
|
title,
|
||||||
|
};
|
||||||
|
await tp.user.util.updateMetadata(tp, metadata);
|
||||||
|
%>
|
||||||
|
|
||||||
|
<% tp.file.cursor() %>
|
||||||
65
zz_meta/templater/ttrpg/region.md
Normal file
65
zz_meta/templater/ttrpg/region.md
Normal file
@ -0,0 +1,65 @@
|
|||||||
|
<%*
|
||||||
|
const thisFile = tp.config.target_file;
|
||||||
|
const campaignData = tp.user.ttrpg.campaignData(thisFile)
|
||||||
|
const settingData = tp.user.ttrpg.settingData(thisFile);
|
||||||
|
const title = tp.file.title === "Untitled"
|
||||||
|
? await tp.system.prompt("Region Name")
|
||||||
|
: tp.file.title;
|
||||||
|
const adjective = tp.frontmatter?.adjective ?? "";
|
||||||
|
const types = [
|
||||||
|
"nation",
|
||||||
|
"duchy",
|
||||||
|
"county",
|
||||||
|
"state",
|
||||||
|
"star system",
|
||||||
|
"planet",
|
||||||
|
"sector",
|
||||||
|
"continent",
|
||||||
|
];
|
||||||
|
const govTypes = [
|
||||||
|
"anarchy",
|
||||||
|
"athenian democracy",
|
||||||
|
"caste",
|
||||||
|
"city-states",
|
||||||
|
"clan/tribal",
|
||||||
|
"corporate state",
|
||||||
|
"dictatorship",
|
||||||
|
"feudal",
|
||||||
|
"hive mind",
|
||||||
|
"representative democracy",
|
||||||
|
"technocracy",
|
||||||
|
"theocracy",
|
||||||
|
"bureaucracy",
|
||||||
|
"charismatic rule",
|
||||||
|
"cybercracy/machine civilization",
|
||||||
|
"meritocracy",
|
||||||
|
"military government",
|
||||||
|
"oligarchy",
|
||||||
|
"thaumatocracy",
|
||||||
|
];
|
||||||
|
const type = tp.frontmatter.regionType ?? await tp.system.suggester(v => v, types, true, "Type of Region");
|
||||||
|
const metadata = {
|
||||||
|
tags: ['ttrpg/place/region'],
|
||||||
|
data: {
|
||||||
|
icon: "map",
|
||||||
|
title,
|
||||||
|
pronunciation: tp.frontmatter.pronunciation ?? "",
|
||||||
|
summary: tp.frontmatter?.summary ?? "",
|
||||||
|
campaigns: [campaignData.link],
|
||||||
|
setting: settingData.link,
|
||||||
|
regionType: type,
|
||||||
|
capital: tp.frontmatter?.capital ?? "",
|
||||||
|
location: tp.frontmatter?.location ?? "",
|
||||||
|
population: tp.frontmatter?.population ?? 0,
|
||||||
|
government: tp.frontmatter?.government ?? (await tp.system.suggester(v => v, govTypes, false, "Type of Government")) ?? "",
|
||||||
|
leader: tp.frontmatter?.leader ?? "",
|
||||||
|
adjective: tp.frontmatter?.adjective ?? "",
|
||||||
|
},
|
||||||
|
title,
|
||||||
|
};
|
||||||
|
await tp.user.util.updateMetadata(tp, metadata);
|
||||||
|
%>
|
||||||
|
|
||||||
|
<% tp.file.cursor() %>
|
||||||
|
|
||||||
|
![[zz_meta/bases/ttrpg/RegionInfo.base#Places|RegionInfo]]
|
||||||
52
zz_meta/templater/ttrpg/session.md
Normal file
52
zz_meta/templater/ttrpg/session.md
Normal file
@ -0,0 +1,52 @@
|
|||||||
|
<%*
|
||||||
|
const thisFile = tp.config.target_file;
|
||||||
|
const campaignData = tp.user.ttrpg.campaignData(thisFile)
|
||||||
|
const settingData = tp.user.ttrpg.settingData(thisFile);
|
||||||
|
const sessionNumber = Math.max(0, ...(
|
||||||
|
tp.user.util.filesWithTag("ttrpg/session")
|
||||||
|
.filter(f => tp.user.util.frontmatterLinksToTFiles(f, 'campaigns').includes(campaignData.file))
|
||||||
|
.map(f => tp.user.util.getFileProperty(f, "sessionNumber"))
|
||||||
|
.filter(n => n === 0 || n) || 0)
|
||||||
|
) + 1;
|
||||||
|
const title = tp.file.title === "Untitled" ? `Session ${sessionNumber}` : tp.file.title;
|
||||||
|
let padSessionNumber = `${sessionNumber}`
|
||||||
|
while (padSessionNumber.length < 3) {
|
||||||
|
padSessionNumber = `0${padSessionNumber}`
|
||||||
|
}
|
||||||
|
const metadata = {
|
||||||
|
tags: ["ttrpg/session"],
|
||||||
|
data: {
|
||||||
|
icon: "book-open",
|
||||||
|
title,
|
||||||
|
gm: campaignData.gm,
|
||||||
|
players: campaignData.players,
|
||||||
|
sessionNumber,
|
||||||
|
summary: "",
|
||||||
|
aliases: [
|
||||||
|
title,
|
||||||
|
`${campaignData?.title} ${title}`
|
||||||
|
],
|
||||||
|
campaigns: [campaignData.link],
|
||||||
|
realDate: tp.date.now('YYYY-MM-DD')
|
||||||
|
},
|
||||||
|
title: `Session ${padSessionNumber}_${tp.date.now('YYYY-MM-DD')}`
|
||||||
|
};
|
||||||
|
if (settingData?.calendar) {
|
||||||
|
metadata.data["fc-calendar"] = settingData.calendar;
|
||||||
|
metadata.data["fc-display-name"] = `${campaignData?.title} ${title}`;
|
||||||
|
metadata.data["fc-date"] = "";
|
||||||
|
metadata.data["fc-end"] = "";
|
||||||
|
metadata.data["fc-category"] = `${campaignData?.title}`;
|
||||||
|
}
|
||||||
|
await tp.user.util.updateMetadata(tp, metadata);
|
||||||
|
%>
|
||||||
|
## Recap
|
||||||
|
|
||||||
|
- <% tp.file.cursor() %>
|
||||||
|
|
||||||
|
## Session Info
|
||||||
|
|
||||||
|
-
|
||||||
|
|
||||||
|
---
|
||||||
|
![[SessionInfo.base#Navigation]]
|
||||||
31
zz_meta/templater/ttrpg/setting.md
Normal file
31
zz_meta/templater/ttrpg/setting.md
Normal file
@ -0,0 +1,31 @@
|
|||||||
|
<%*
|
||||||
|
const title = (
|
||||||
|
tp.file.title === "Untitled"
|
||||||
|
? await tp.system.prompt("Setting Title")
|
||||||
|
: tp.file.title
|
||||||
|
);
|
||||||
|
const calendarId = (
|
||||||
|
tp.frontmatter?.["fc-calendar"]
|
||||||
|
? tp.frontmatter["fc-calendar"]
|
||||||
|
: await tp.system.prompt("Setting Calendar ID", title)
|
||||||
|
)
|
||||||
|
const metadata = {
|
||||||
|
title,
|
||||||
|
tags: ["ttrpg/setting"],
|
||||||
|
data: {
|
||||||
|
icon: "globe",
|
||||||
|
title,
|
||||||
|
"fc-calendar": calendarId,
|
||||||
|
pdfs: tp.frontmatter.pdfs ?? [],
|
||||||
|
},
|
||||||
|
title,
|
||||||
|
};
|
||||||
|
await tp.user.util.updateMetadata(tp, metadata);
|
||||||
|
%>
|
||||||
|
![[SystemSettingCampaigns.base]]
|
||||||
|
|
||||||
|
<% tp.file.cursor() %>
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
![[PDFinfo.base]]
|
||||||
69
zz_meta/templater/ttrpg/settlement.md
Normal file
69
zz_meta/templater/ttrpg/settlement.md
Normal file
@ -0,0 +1,69 @@
|
|||||||
|
<%*
|
||||||
|
const thisFile = tp.config.target_file;
|
||||||
|
const campaignData = tp.user.ttrpg.campaignData(thisFile)
|
||||||
|
const settingData = tp.user.ttrpg.settingData(thisFile);
|
||||||
|
const title = tp.file.title === "Untitled"
|
||||||
|
? await tp.system.prompt("Settlement Name")
|
||||||
|
: tp.file.title;
|
||||||
|
const adjective = tp.frontmatter?.adjective ?? "";
|
||||||
|
const types = [
|
||||||
|
"thorp",
|
||||||
|
"hamlet",
|
||||||
|
"village",
|
||||||
|
"small town",
|
||||||
|
"large town",
|
||||||
|
"city ward",
|
||||||
|
"neighborhood",
|
||||||
|
"small city",
|
||||||
|
"large city",
|
||||||
|
"metropolis",
|
||||||
|
];
|
||||||
|
const govTypes = [
|
||||||
|
"anarchy",
|
||||||
|
"athenian democracy",
|
||||||
|
"caste",
|
||||||
|
"clan/tribal",
|
||||||
|
"corporate state",
|
||||||
|
"dictatorship",
|
||||||
|
"feudal",
|
||||||
|
"hive mind",
|
||||||
|
"representative democracy",
|
||||||
|
"technocracy",
|
||||||
|
"theocracy",
|
||||||
|
"bureaucracy",
|
||||||
|
"charismatic rule",
|
||||||
|
"cybercracy/machine civilization",
|
||||||
|
"meritocracy",
|
||||||
|
"military government",
|
||||||
|
"oligarchy",
|
||||||
|
"thaumatocracy",
|
||||||
|
];
|
||||||
|
const type = tp.frontmatter.settlementType ?? await tp.system.suggester(v => v, types, true, "Type of Settlement");
|
||||||
|
const metadata = {
|
||||||
|
tags: ['ttrpg/place/settlement'],
|
||||||
|
data: {
|
||||||
|
icon: "building-2",
|
||||||
|
title,
|
||||||
|
pronunciation: tp.frontmatter.pronunciation ?? "",
|
||||||
|
summary: tp.frontmatter?.summary ?? "",
|
||||||
|
campaigns: [campaignData.link],
|
||||||
|
setting: settingData.link,
|
||||||
|
settlementType: type,
|
||||||
|
location: tp.frontmatter?.location ?? "",
|
||||||
|
population: tp.frontmatter?.population ?? 0,
|
||||||
|
government: tp.frontmatter?.government ?? (await tp.system.suggester(v => v, govTypes, false, "Type of Government")) ?? "",
|
||||||
|
leader: tp.frontmatter?.leader ?? "",
|
||||||
|
residents: tp.frontmatter?.residents ?? [],
|
||||||
|
adjective: tp.frontmatter?.adjective ?? "",
|
||||||
|
},
|
||||||
|
title,
|
||||||
|
};
|
||||||
|
await tp.user.util.updateMetadata(tp, metadata);
|
||||||
|
%>
|
||||||
|
|
||||||
|
<% tp.file.cursor() %>
|
||||||
|
|
||||||
|
![[zz_meta/bases/ttrpg/SettlementInfo.base#Places|SettlementInfo]]
|
||||||
|
|
||||||
|
![[zz_meta/bases/ttrpg/SettlementInfo.base#People|SettlementInfo]]
|
||||||
|
|
||||||
24
zz_meta/templater/ttrpg/system.md
Normal file
24
zz_meta/templater/ttrpg/system.md
Normal file
@ -0,0 +1,24 @@
|
|||||||
|
<%*
|
||||||
|
const title = (
|
||||||
|
tp.file.title === "Untitled"
|
||||||
|
? await tp.system.prompt("System Title")
|
||||||
|
: tp.file.title
|
||||||
|
);
|
||||||
|
const metadata = {
|
||||||
|
title,
|
||||||
|
tags: ["ttrpg/system"],
|
||||||
|
data: {
|
||||||
|
icon: "notebook",
|
||||||
|
title,
|
||||||
|
pdfs: tp.frontmatter.pdfs ?? [],
|
||||||
|
},
|
||||||
|
};
|
||||||
|
await tp.user.util.updateMetadata(tp, metadata);
|
||||||
|
%>
|
||||||
|
![[SystemSettingCampaigns.base]]
|
||||||
|
|
||||||
|
<% tp.file.cursor() %>
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
![[PDFinfo.base]]
|
||||||
16
zz_meta/utility/Leaflet Bounds Calculator.md
Normal file
16
zz_meta/utility/Leaflet Bounds Calculator.md
Normal file
@ -0,0 +1,16 @@
|
|||||||
|
---
|
||||||
|
image:
|
||||||
|
height: 768
|
||||||
|
width: 1024
|
||||||
|
pixelDistance: 100
|
||||||
|
unitDistance: 12
|
||||||
|
---
|
||||||
|
**Image Height:** `INPUT[number:image.height]`px
|
||||||
|
**Image Width:** `INPUT[number:image.width]`px
|
||||||
|
**Distance:** `INPUT[number:image.pixelDistance]`pixels = `INPUT[number:image.unitDistance]`units (feet, miles, km, parsecs, etc)
|
||||||
|
|
||||||
|
**Lower Bound:** 0, 0
|
||||||
|
**Upper Bound:** `VIEW[round({image.height}/({image.pixelDistance}/{image.unitDistance}), 3)][math]`, `VIEW[round({image.width}/({image.pixelDistance}/{image.unitDistance}), 3)][math]`
|
||||||
|
**Center Point:** `VIEW[round({image.height}/({image.pixelDistance}/{image.unitDistance})/2, 3)][math]`, `VIEW[round({image.width}/({image.pixelDistance}/{image.unitDistance})/2, 3)][math]`
|
||||||
|
|
||||||
|
|
||||||
Loading…
x
Reference in New Issue
Block a user