From 669bbc5d387801fc2584edd631a49b24c163a419 Mon Sep 17 00:00:00 2001 From: Zee Date: Mon, 19 Feb 2024 09:56:25 +0200 Subject: [PATCH 1/3] Add pack metadata to editor pack properties and C2G export --- js/editor/dialogs.js | 10 +++++++++- js/editor/main.js | 11 +++++++++++ js/format-base.js | 1 + js/format-c2g.js | 13 +++++++++++++ 4 files changed, 34 insertions(+), 1 deletion(-) diff --git a/js/editor/dialogs.js b/js/editor/dialogs.js index 336eaae..8449dd6 100644 --- a/js/editor/dialogs.js +++ b/js/editor/dialogs.js @@ -14,8 +14,13 @@ export class EditorPackMetaOverlay extends DialogOverlay { dl.append( mk('dt', "Title"), mk('dd', mk('input', {name: 'title', type: 'text', value: stored_pack.title})), + mk('dt', "Author"), + mk('dd', mk('input', {name: 'author', type: 'text', value: stored_pack.metadata.by ?? ""})), + mk('dt', "Description"), + mk('dd.-textarea', mk('textarea', {name: 'description'}, stored_pack.metadata.description ?? "")), + mk('dt', "Difficulty"), + mk('dd', mk('input', {name: 'difficulty', type: 'number', min: 1, max: 5, step: 0.5, value: stored_pack.metadata.difficulty ?? 3}), " (between 1 and 5)"), ); - // TODO...? what else is a property of the pack itself this.add_button("save", () => { let els = this.root.elements; @@ -25,6 +30,9 @@ export class EditorPackMetaOverlay extends DialogOverlay { stored_pack.title = title; this.conductor.update_level_title(); } + stored_pack.metadata.by = els.author.value || undefined; + stored_pack.metadata.description = els.description.value || undefined; + stored_pack.metadata.difficulty = parseFloat(els.difficulty.value); this.close(); }); diff --git a/js/editor/main.js b/js/editor/main.js index 65ce985..03a1224 100644 --- a/js/editor/main.js +++ b/js/editor/main.js @@ -508,6 +508,15 @@ export class Editor extends PrimaryView { let lines = []; let safe_title = (stored_pack.title || "untitled").replace(/[""]/g, "'").replace(/[\x00-\x1f]+/g, "_"); lines.push(`game "${safe_title}"`); + if (stored_pack.metadata.by) { + lines.push(`; meta by: ${stored_pack.metadata.by}`); + } + if (stored_pack.metadata.description) { + lines.push(`; meta description: ${stored_pack.metadata.description}`); + } + if (stored_pack.metadata.difficulty) { + lines.push(`; meta difficulty: ${stored_pack.metadata.difficulty}`); + } let files = {}; let count = stored_pack.level_metadata.length; @@ -741,6 +750,7 @@ export class Editor extends PrimaryView { let pack_key = stored_pack.editor_metadata.key; this.stash.packs[pack_key] = { title: stored_pack.title, + metadata: stored_pack.metadata, level_count: stored_pack.level_metadata.length, last_modified: Date.now(), }; @@ -824,6 +834,7 @@ export class Editor extends PrimaryView { }); // TODO should this also be in the pack's stash...? stored_pack.title = this.stash.packs[pack_key].title; + stored_pack.metadata = this.stash.packs[pack_key].metadata ?? {}; stored_pack.editor_metadata = { key: pack_key, }; diff --git a/js/format-base.js b/js/format-base.js index f13b453..b7f1b66 100644 --- a/js/format-base.js +++ b/js/format-base.js @@ -154,6 +154,7 @@ export class StoredPack { constructor(identifier, level_loader) { this.identifier = identifier; this.title = ""; + this.metadata = {}; this._level_loader = level_loader; // Simple objects containing keys that are usually: diff --git a/js/format-c2g.js b/js/format-c2g.js index 37741b8..72a9713 100644 --- a/js/format-c2g.js +++ b/js/format-c2g.js @@ -2113,6 +2113,18 @@ class Parser { } } + +function parse_pack_metadata(string) { + let metadata = {}; + for (let match of string.matchAll(/; meta (.+?): (.+)/g)) { + metadata[match[1]] = match[2]; + } + if (metadata.difficulty) { + metadata.difficulty = parseFloat(metadata.difficulty); + } + return metadata; +} + // C2G is a Chip's Challenge 2 format that describes the structure of a level set, which is helpful // since CC2 levels are all stored in separate files // XXX observations i have made about this hell format: @@ -2176,6 +2188,7 @@ const MAX_SIMULTANEOUS_REQUESTS = 5; // FIXME and right off the bat we have an Issue: this is a text format so i want a string, not // an arraybuffer! let contents = util.string_from_buffer_ascii(buf); + game.metadata = parse_pack_metadata(contents); parser = new Parser(contents); let statements = []; let level_number = 1; From c74b8f3f03569df9c08735e93fc6ae70aa692afa Mon Sep 17 00:00:00 2001 From: Zee Date: Mon, 19 Feb 2024 09:58:49 +0200 Subject: [PATCH 2/3] Write all metadata keys when exporting to C2G --- js/editor/main.js | 10 ++-------- 1 file changed, 2 insertions(+), 8 deletions(-) diff --git a/js/editor/main.js b/js/editor/main.js index 03a1224..812654b 100644 --- a/js/editor/main.js +++ b/js/editor/main.js @@ -508,14 +508,8 @@ export class Editor extends PrimaryView { let lines = []; let safe_title = (stored_pack.title || "untitled").replace(/[""]/g, "'").replace(/[\x00-\x1f]+/g, "_"); lines.push(`game "${safe_title}"`); - if (stored_pack.metadata.by) { - lines.push(`; meta by: ${stored_pack.metadata.by}`); - } - if (stored_pack.metadata.description) { - lines.push(`; meta description: ${stored_pack.metadata.description}`); - } - if (stored_pack.metadata.difficulty) { - lines.push(`; meta difficulty: ${stored_pack.metadata.difficulty}`); + for (let [key, value] of Object.entries(stored_pack.metadata)) { + lines.push(`; meta ${key}: ${value}`) } let files = {}; From 394faa2f793920550f9a27829f0c16f57986157c Mon Sep 17 00:00:00 2001 From: Zee Date: Mon, 19 Feb 2024 09:59:51 +0200 Subject: [PATCH 3/3] Add missing semicolor --- js/editor/main.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/js/editor/main.js b/js/editor/main.js index 812654b..adad4db 100644 --- a/js/editor/main.js +++ b/js/editor/main.js @@ -509,7 +509,7 @@ export class Editor extends PrimaryView { let safe_title = (stored_pack.title || "untitled").replace(/[""]/g, "'").replace(/[\x00-\x1f]+/g, "_"); lines.push(`game "${safe_title}"`); for (let [key, value] of Object.entries(stored_pack.metadata)) { - lines.push(`; meta ${key}: ${value}`) + lines.push(`; meta ${key}: ${value}`); } let files = {};