tangled
alpha
login
or
join now
vielle.dev
/
dnd-astral-powers
0
fork
atom
this repo has no description
0
fork
atom
overview
issues
pulls
pipelines
add point counter
vielle.dev
1 month ago
bddffbc0
63693774
verified
This commit was signed with the committer's
known signature
.
vielle.dev
SSH Key Fingerprint:
SHA256:/4bvxqoEh9iMdjAPgcgAgXKZZQTROL3ULiPt6nH9RSs=
+178
2 changed files
expand all
collapse all
unified
split
src
components
astral
Points.astro
pages
astral
index.astro
+171
src/components/astral/Points.astro
···
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
0
···
1
+
---
2
+
3
+
---
4
+
5
+
<script>
6
+
import Powers, { type powerObj } from "../../lib/powers";
7
+
8
+
class HTMLPointsMeterElement extends HTMLElement {
9
+
dec: HTMLButtonElement;
10
+
inc: HTMLButtonElement;
11
+
meter: HTMLMeterElement;
12
+
count: HTMLElement;
13
+
max: HTMLElement;
14
+
15
+
constructor() {
16
+
super();
17
+
const dec = this.querySelector("button[data-dec]");
18
+
const inc = this.querySelector("button[data-inc]");
19
+
const meter = this.querySelector("meter");
20
+
const count = this.querySelector("span.count");
21
+
const max = this.querySelector("span.max");
22
+
23
+
if (
24
+
!(
25
+
dec instanceof HTMLButtonElement &&
26
+
inc instanceof HTMLButtonElement &&
27
+
meter instanceof HTMLMeterElement &&
28
+
count instanceof HTMLElement &&
29
+
max instanceof HTMLElement
30
+
)
31
+
) {
32
+
throw "Elements not set correctly";
33
+
}
34
+
35
+
this.dec = dec;
36
+
this.inc = inc;
37
+
this.meter = meter;
38
+
this.count = count;
39
+
this.max = max;
40
+
41
+
Powers.subscribe(this.handleState.bind(this));
42
+
43
+
this.dec.addEventListener("click", async () => {
44
+
this.max.innerText = "...";
45
+
this.dec.disabled = true;
46
+
47
+
await Powers.setKey("points", Powers.get().points - 1).catch((e) =>
48
+
console.warn(e),
49
+
);
50
+
51
+
this.dec.disabled = !(
52
+
Powers.get().points - 1 >= 0 &&
53
+
Powers.get().points - 1 >= Powers.get().powers.length
54
+
);
55
+
});
56
+
57
+
this.inc.addEventListener("click", async () => {
58
+
this.max.innerText = "...";
59
+
this.inc.disabled = true;
60
+
await Powers.setKey("points", Powers.get().points + 1).catch((e) =>
61
+
console.warn(e),
62
+
);
63
+
64
+
this.inc.disabled = false;
65
+
});
66
+
}
67
+
68
+
handleState(_val: Readonly<powerObj> | null) {
69
+
const val = _val ? _val : { powers: [""], points: 1 };
70
+
this.meter.value = val.powers.length;
71
+
this.meter.max = val.points;
72
+
this.count.innerText = val.powers.length + "";
73
+
this.max.innerText = val.points + "";
74
+
75
+
this.dec.disabled = !(
76
+
val.points - 1 >= 0 && val.points - 1 >= val.powers.length
77
+
);
78
+
}
79
+
}
80
+
81
+
customElements.define("points-meter", HTMLPointsMeterElement);
82
+
</script>
83
+
84
+
<points-meter>
85
+
<button aria-label="decrement" data-dec>-</button>
86
+
<meter></meter>
87
+
<span class="total"
88
+
><span class="count"></span>/<span class="max"></span></span
89
+
>
90
+
<button aria-label="increment" data-inc>+</button>
91
+
</points-meter>
92
+
93
+
<style>
94
+
points-meter {
95
+
background-color: color-mix(
96
+
in oklch,
97
+
100% var(--background),
98
+
10% var(--text)
99
+
);
100
+
border: 5px solid var(--text);
101
+
border-radius: 10px;
102
+
padding: 1em;
103
+
z-index: 99;
104
+
105
+
display: grid;
106
+
gap: 1em;
107
+
grid-template: "dec meter inc" 1fr / 1fr 3fr 1fr;
108
+
max-width: 100%;
109
+
width: 400px;
110
+
111
+
button {
112
+
background-color: inherit;
113
+
border: 3px solid;
114
+
border-color: inherit;
115
+
border-radius: inherit;
116
+
117
+
&[disabled],
118
+
&:active {
119
+
opacity: 0.7;
120
+
}
121
+
}
122
+
123
+
.total {
124
+
width: min-content;
125
+
padding: 0.2em 1em;
126
+
margin: auto;
127
+
z-index: 99;
128
+
129
+
background: var(--background);
130
+
border: 1px solid;
131
+
border-color: inherit;
132
+
border-radius: 0.5em;
133
+
}
134
+
135
+
meter {
136
+
appearance: none;
137
+
width: 100%;
138
+
height: 3rem;
139
+
background: var(--background);
140
+
border-radius: 10px;
141
+
overflow: clip;
142
+
143
+
&::-webkit-meter-bar {
144
+
background: inherit;
145
+
height: 3rem;
146
+
}
147
+
148
+
&::-moz-meter-bar {
149
+
background: var(--green);
150
+
}
151
+
152
+
&::-webkit-meter-optimum-value {
153
+
background: var(--green);
154
+
height: 100%;
155
+
}
156
+
}
157
+
158
+
button[data-dec] {
159
+
grid-area: dec;
160
+
}
161
+
162
+
button[data-inc] {
163
+
grid-area: inc;
164
+
}
165
+
166
+
meter,
167
+
.total {
168
+
grid-area: meter;
169
+
}
170
+
}
171
+
</style>
+7
src/pages/astral/index.astro
···
1
---
2
import Base from "../../Base.astro";
0
3
import Powers from "../../components/astral/Powers.astro";
4
import { powerData, powers, powerTree } from "../../consts/astral";
5
---
···
37
38
body {
39
margin: 2em 0 2em 10em;
0
0
0
0
40
}
41
</style>
0
0
42
43
<Powers {...powerTree} i={0} siblings={1} />
44
</Base>
···
1
---
2
import Base from "../../Base.astro";
3
+
import Points from "../../components/astral/Points.astro";
4
import Powers from "../../components/astral/Powers.astro";
5
import { powerData, powers, powerTree } from "../../consts/astral";
6
---
···
38
39
body {
40
margin: 2em 0 2em 10em;
41
+
display: flex;
42
+
flex-direction: column;
43
+
align-items: center;
44
+
gap: 5em;
45
}
46
</style>
47
+
48
+
<Points />
49
50
<Powers {...powerTree} i={0} siblings={1} />
51
</Base>