updated the character form

This commit is contained in:
Lukas Forsberg 2025-11-30 22:32:40 +01:00
parent 3c10555577
commit 0339054f73
3 changed files with 219 additions and 77 deletions

View File

@ -16,8 +16,14 @@
characterData.Connections ??= [];
characterData.RangedWeapons ??= [];
characterData.MeleeWeapons ??= [];
characterData.Armor ??= [];
characterData.Cyberware ??= [];
characterData.Bioware ??= [];
characterData.PositiveQualities ??= [];
characterData.NegativeQualities ??= [];
characterData.PysicalCondition ??= Defaults.PysicalCondition
characterData.StunCondition ??= Defaults.StunCondition
characterData.Notes ??= ""
const characterInfoTypes = {
Metatype: "text",
@ -60,10 +66,10 @@
let inventory = currentCharacter?.inventory || [];
</script>
<h1>Name: {currentCharacter.name}</h1>
<h2>Character Info</h2>
<div class="info-container">
{#each Object.entries(characterData.Info) as [key, value], i}
<div class="input-row">
<label for={"field-" + i}>{key}</label>
@ -71,11 +77,14 @@
id={"field-" + i}
type={characterInfoTypes[key]}
bind:value={characterData.Info[key]}
min={characterInfoTypes[key] === "number" ? 0 : null} />
min={characterInfoTypes[key] === "number" ? 0 : null}
max={characterInfoTypes[key] === "number" ? 100 : null} />
</div>
{/each}
</div>
<h2>Attributes</h2>
<div class="info-container">
{#each Object.entries(characterData.Attributes) as [key, value], i}
<div class="input-row">
<label for={"field-" + i}>{key}</label>
@ -83,11 +92,12 @@
id={"field-" + i}
type="number"
bind:value={characterData["Attributes"][key]}
min=0 />
min=0
max=100 />
</div>
{/each}
</div>
<div class="skill-form-container">
<h2>Skills</h2>
<table>
<thead>
@ -122,7 +132,6 @@
</table>
<button on:click={() => add("Skills")}>+</button>
<h2>Contacts</h2>
<table>
<thead>
@ -218,93 +227,203 @@
</table>
<button on:click={() => add("MeleeWeapons")}>+</button>
<h2>Cyberware</h2>
<div class="skill-headers">
<span class="col-name">Cyberware</span>
<span class="col-value">Rating</span>
<span class="col-value">Essence</span>
<span class="col-value">Notes</span>
<span></span> <!-- for remove button -->
</div>
{#each characterData.Cyberware as Cyberware, i}
<div class="skill-entry">
<input class="col-name" placeholder="Cyberware" bind:value={characterData.Cyberware[i].Implant} />
<input class="col-value" type="number" min="0" bind:value={characterData.Cyberware[i].Rating} />
<input class="col-value" type="number" min="0" bind:value={characterData.Cyberware[i].Essence} />
<input class="col-value" placeholder="Notes" bind:value={characterData.Cyberware[i].Notes} />
<button on:click={() => remove("Cyberware", i)}>X</button>
</div>
<h2>Armor</h2>
<table>
<thead>
<tr>
<th>Armor</th>
<th>Ballistic</th>
<th>Impact</th>
<th>Page</th>
<th></th>
<th></th>
</tr>
</thead>
<tbody>
{#each characterData.Armor as armor, i}
<tr>
<td><input placeholder="Armor" bind:value={characterData.Armor[i].Armor} /></td>
<td><input type="number" min=0 max=100 bind:value={characterData.Armor[i].Ballistic} /></td>
<td><input type="number" min=0 max=100 bind:value={characterData.Armor[i].Impact} /></td>
<td><input type="number" min=1 max=354 bind:value={characterData.Armor[i].Page} /></td>
<td><button on:click={() => viewPage(characterData.Armor[i].Page)}>View</button></td>
<td><button on:click={() => remove("Armor", i)}>X</button></td>
</tr>
{/each}
<button on:click={() => add("Cyberware")}>Add Cyberware</button>
</tbody>
</table>
<button on:click={() => add("Armor")}>+</button>
<h2>Cyberware</h2>
<table>
<thead>
<tr>
<th>Cyberware</th>
<th>Rating</th>
<th>Essence</th>
<th>Notes</th>
<th>Page</th>
<th></th>
<th></th> <!-- for remove button -->
</tr>
</thead>
<tbody>
{#each characterData.Cyberware as Cyberware, i}
<tr>
<td><input placeholder="Cyberware" bind:value={characterData.Cyberware[i].Implant} /></td>
<td><input type="number" min=0 max=100 bind:value={characterData.Cyberware[i].Rating} /></td>
<td><input type="number" min=0 max=100 bind:value={characterData.Cyberware[i].Essence} /></td>
<td><input placeholder="Notes" bind:value={characterData.Cyberware[i].Notes} /></td>
<td><input type="number" min=1 max=354 bind:value={characterData.Connections[i].Page} /></td>
<td><button on:click={() => viewPage(characterData.Connections[i].Page)}>View</button></td>
<td><button on:click={() => remove("Cyberware", i)}>X</button></td>
</tr>
{/each}
</tbody>
</table>
<button on:click={() => add("Cyberware")}>+</button>
<h2>Bioware</h2>
<div class="skill-headers">
<span class="col-name">Bioware</span>
<span class="col-value">Rating</span>
<span class="col-value">Essence</span>
<span class="col-name">Notes</span>
<span></span> <!-- for remove button -->
</div>
<table>
<thead>
<tr>
<th>Bioware</th>
<th>Rating</th>
<th>Essence</th>
<th>Notes</th>
<th>Page</th>
<th></th>
<th></th> <!-- for remove button -->
</tr>
</thead>
<tbody>
{#each characterData.Bioware as Bioware, i}
<div class="skill-entry">
<input class="col-name" placeholder="Bioware" bind:value={characterData.Bioware[i].Implant} />
<input class="col-value" type="number" min="0" bind:value={characterData.Bioware[i].Rating} />
<input class="col-value" type="number" min="0" bind:value={characterData.Bioware[i].Essence} />
<input class="col-name" placeholder="Notes" bind:value={characterData.Bioware[i].Notes} />
<button on:click={() => remove("Bioware", i)}>X</button>
</div>
<tr>
<td><input placeholder="Bioware" bind:value={characterData.Bioware[i].Implant} /></td>
<td><input type="number" min="0" bind:value={characterData.Bioware[i].Rating} /></td>
<td><input type="number" min="0" bind:value={characterData.Bioware[i].Essence} /></td>
<td><input placeholder="Notes" bind:value={characterData.Bioware[i].Notes} /></td>
<td><input type="number" min=1 max=354 bind:value={characterData.Connections[i].Page} /></td>
<td><button on:click={() => viewPage(characterData.Connections[i].Page)}>View</button></td>
<td><button on:click={() => remove("Bioware", i)}>X</button></td>
</tr>
{/each}
<button on:click={() => add("Bioware")}>Add Bioware</button>
</tbody>
</table>
<button on:click={() => add("Bioware")}>+</button>
<h2>Qualities</h2>
<h3>Positive</h3>
<table>
<thead>
<tr>
<th>Quality</th>
<th>Page</th>
<th></th>
<th></th> <!-- for remove button -->
</tr>
</thead>
<tbody>
{#each characterData.PositiveQualities as qualitiy, i}
<tr>
<td><input placeholder="Qualitiy" bind:value={characterData.PositiveQualities[i].Qualitiy} /></td>
<td><input type="number" min=1 max=354 bind:value={characterData.PositiveQualities[i].Page} /></td>
<td><button on:click={() => viewPage(characterData.PositiveQualities[i].Page)}>View</button></td>
<td><button on:click={() => remove("PositiveQualities", i)}>X</button></td>
</tr>
{/each}
</tbody>
</table>
<button on:click={() => add("PositiveQualities")}>+</button>
<h3>Negative</h3>
<table>
<thead>
<tr>
<th>Quality</th>
<th>Page</th>
<th></th>
<th></th> <!-- for remove button -->
</tr>
</thead>
<tbody>
{#each characterData.NegativeQualities as qualitiy, i}
<tr>
<td><input placeholder="Qualitiy" bind:value={characterData.NegativeQualities[i].Qualitiy} /></td>
<td><input type="number" min=1 max=354 bind:value={characterData.NegativeQualities[i].Page} /></td>
<td><button on:click={() => viewPage(characterData.NegativeQualities[i].Page)}>View</button></td>
<td><button on:click={() => remove("NegativeQualities", i)}>X</button></td>
</tr>
{/each}
</tbody>
</table>
<button on:click={() => add("NegativeQualities")}>+</button>
<h2>Pysical Condition</h2>
<table>
<tbody>
{#each characterData.PysicalCondition as row, rowIndex}
<tr>
{#each row as cell, colIndex}
<td>
<input
type="checkbox"
bind:checked={characterData.PysicalCondition[rowIndex][colIndex]}
/>
</td>
{/each}
</tr>
{/each}
</tbody>
</table>
<h2>Stun Condition</h2>
<table>
<tbody>
{#each characterData.StunCondition as row, rowIndex}
<tr>
{#each row as cell, colIndex}
<td>
<input
type="checkbox"
bind:checked={characterData.StunCondition[rowIndex][colIndex]}
/>
</td>
{/each}
</tr>
{/each}
</tbody>
</table>
<h2>Notes</h2>
<div>
<textarea
id="notes"
bind:value={characterData.Notes}
rows="10"
cols="100"
placeholder="Write your character notes here..."
></textarea>
</div>
<button on:click={saveCharacterData}>Save</button>
<style>
.skill-form-container {
width: 100%; /* 100% of the screen */
max-width: 1200px; /* optional, limits width on large screens */
}
.skill-headers, .skill-entry {
.info-container {
display: flex;
flex-wrap: wrap; /* allows items to go to next line if needed */
gap: 0.5em; /* space between each input-row */
}
.input-row {
display: flex;
gap: 0.3rem;
align-items: center;
flex-wrap: wrap; /* allow wrapping on small screens */
}
.skill-headers {
font-weight: bold;
margin-bottom: 0.3rem;
}
.skill-headers span {
padding: 0;
margin: 0;
}
.skill-headers span,
.skill-entry input,
.skill-entry select,
.skill-entry span {
box-sizing: border-box;
}
.col-name {
flex: 2;
min-width: 80px;
}
.col-value {
flex: 1;
min-width: 40px;
gap: 0.5em; /* space between label and input */
}
th {
text-align: left;
}
.col-remove {
flex: 0;
}
</style>

View File

@ -65,6 +65,22 @@ const Implant = {
Notes: "",
}
const Qualitiy = {
Qualitiy : ""
}
const PysicalCondition = Array.from({ length: 6 }, () =>
Array.from({ length: 3 }, () => false))
const StunCondition = Array.from({ length: 4 }, () =>
Array.from({ length: 3 }, () => false))
const Armor = {
Armor: "",
Ballistic: 0,
Impact: 0
}
export const Defaults = {
Info: Info,
Attributes: Attributes,
@ -74,6 +90,11 @@ export const Defaults = {
MeleeWeapons : MeleeWeapon,
Cyberware : Implant,
Bioware : Implant,
PositiveQualities : Qualitiy,
NegativeQualities : Qualitiy,
PysicalCondition : PysicalCondition,
StunCondition : StunCondition,
Armor : Armor,
}

View File

@ -21,6 +21,8 @@ namespace shadowrun {
MeleeWeapons = 6,
Cyberware = 7,
Bioware = 8,
PositiveQualities = 9,
NegativeQualities = 10,
};
struct ShadowrunCharacter {