@roxyapi/ui 0.7.0 → 0.8.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/AGENTS.md +35 -52
- package/README.md +99 -41
- package/dist/cdn/components/bodygraph.js +54 -0
- package/dist/cdn/components/bodygraph.js.map +7 -0
- package/dist/cdn/components/forecast-timeline.js +45 -0
- package/dist/cdn/components/forecast-timeline.js.map +7 -0
- package/dist/cdn/roxy-ui.js +49 -40
- package/dist/cdn/roxy-ui.js.map +4 -4
- package/dist/components/bodygraph.d.ts +27 -0
- package/dist/components/bodygraph.d.ts.map +1 -0
- package/dist/components/bodygraph.js +11 -0
- package/dist/components/bodygraph.js.map +7 -0
- package/dist/components/forecast-timeline.d.ts +38 -0
- package/dist/components/forecast-timeline.d.ts.map +1 -0
- package/dist/components/forecast-timeline.js +2 -0
- package/dist/components/forecast-timeline.js.map +7 -0
- package/dist/index.cjs +45 -36
- package/dist/index.cjs.map +4 -4
- package/dist/index.d.ts +2 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +52 -43
- package/dist/index.js.map +4 -4
- package/dist/manifest.d.ts.map +1 -1
- package/dist/manifest.json +2 -0
- package/dist/types/index.d.ts +1 -1
- package/dist/types/index.d.ts.map +1 -1
- package/dist/types/types.gen.d.ts +3994 -6
- package/dist/types/types.gen.d.ts.map +1 -1
- package/dist/utils/bodygraph-render.d.ts +105 -0
- package/dist/utils/bodygraph-render.d.ts.map +1 -0
- package/dist/version.d.ts +1 -1
- package/package.json +1 -1
- package/src/components/bodygraph.ts +390 -0
- package/src/components/forecast-timeline.ts +336 -0
- package/src/index.ts +4 -0
- package/src/manifest.ts +26 -0
- package/src/types/index.ts +1 -1
- package/src/types/types.gen.ts +4079 -6
- package/src/utils/bodygraph-render.ts +641 -0
- package/src/version.ts +1 -1
package/AGENTS.md
CHANGED
|
@@ -8,7 +8,7 @@ Live preview: <https://roxyapi.github.io/ui/>. Source of truth for component typ
|
|
|
8
8
|
|
|
9
9
|
## Identity
|
|
10
10
|
|
|
11
|
-
Roxy UI is the official web component library for the RoxyAPI catalog. Components and helpers cover Western astrology, Vedic astrology, numerology, tarot, biorhythm, I Ching, crystals, dreams, angel numbers, with the location helper for geocoding. New endpoints regenerate component types automatically.
|
|
11
|
+
Roxy UI is the official web component library for the RoxyAPI catalog. Components and helpers cover Western astrology, Vedic astrology, numerology, tarot, Human Design, forecast, biorhythm, I Ching, crystals, dreams, angel numbers, with the location helper for geocoding. New endpoints regenerate component types automatically.
|
|
12
12
|
|
|
13
13
|
## Decision tree for picking a component
|
|
14
14
|
|
|
@@ -32,6 +32,8 @@ Map the natural-language request to a component first; fall back to the table be
|
|
|
32
32
|
| "life path number", "expression number", "personal year", "numerology chart" | `<roxy-numerology-card>` |
|
|
33
33
|
| "draw a tarot card", "card of the day", "card meaning" | `<roxy-tarot-card>` |
|
|
34
34
|
| "tarot reading", "three-card spread", "Celtic Cross", "yes or no tarot" | `<roxy-tarot-spread>` |
|
|
35
|
+
| "Human Design chart", "bodygraph", "my type and authority", "defined centers", "channels and gates" | `<roxy-bodygraph>` |
|
|
36
|
+
| "forecast", "what is coming up", "upcoming transits and events", "timeline of my year" | `<roxy-forecast-timeline>` |
|
|
35
37
|
| "biorhythm", "physical/emotional/intellectual cycle", "critical days" | `<roxy-biorhythm-chart>` |
|
|
36
38
|
| "I Ching", "hexagram", "cast the coins", "Book of Changes" | `<roxy-hexagram>` |
|
|
37
39
|
| "moon phase", "moon calendar", "next full moon", "current moon" | `<roxy-moon-phase>` |
|
|
@@ -72,6 +74,8 @@ Use the table below for the formal endpoint to component mapping.
|
|
|
72
74
|
| `<roxy-numerology-card>` | Numerology | POST /numerology/{life-path,expression,personal-year,chart} | Life path, expression, personal year, full chart |
|
|
73
75
|
| `<roxy-tarot-card>` | Tarot | GET /tarot/cards/{id}, POST /tarot/daily | Single card with upright and reversed flip |
|
|
74
76
|
| `<roxy-tarot-spread>` | Tarot | POST /tarot/spreads/{three-card,celtic-cross,love}, /tarot/yes-no, /tarot/draw | Spreads with positions and reading |
|
|
77
|
+
| `<roxy-bodygraph>` | Human Design | POST /human-design/bodygraph | Nine-center chart with defined and open centers, active channels, gates, and a type and authority summary |
|
|
78
|
+
| `<roxy-forecast-timeline>` | Forecast | POST /forecast/timeline | Date-grouped events across Western, Vedic, and biorhythm domains, weighted by significance |
|
|
75
79
|
| `<roxy-biorhythm-chart>` | Biorhythm | POST /biorhythm/{daily,forecast,critical-days} | Daily bars, forecast cycle lines, critical days |
|
|
76
80
|
| `<roxy-hexagram>` | I Ching | GET /iching/hexagrams/{number}, /iching/cast, POST /iching/daily, /iching/daily/cast | Hexagram with trigrams, judgment, image, changing lines |
|
|
77
81
|
| `<roxy-endpoint-form>` | Helper | Any endpoint via x-roxy-ui hints | Schema-driven form, emits roxy-submit |
|
|
@@ -116,16 +120,13 @@ const { data: chart } = await roxy.astrology.generateNatalChart({
|
|
|
116
120
|
|
|
117
121
|
Every chart endpoint accepts `timezone` as either a decimal-hour offset (`5.5` for IST, `-5` for EST) or an IANA name (`'Asia/Kolkata'`, `'America/New_York'`). The decimal form is what `/location/search` returns; the IANA form is correct over DST boundaries. Pick one and stay consistent in a single integration. Mixing them does not break the API but makes the bug surface area larger.
|
|
118
122
|
|
|
119
|
-
### 4.
|
|
123
|
+
### 4. API key in the browser
|
|
120
124
|
|
|
121
|
-
|
|
125
|
+
Keys are server side only. Call `createRoxy(process.env.ROXY_API_KEY!)` on your server (Node, Bun, Hono, Next.js route handlers, Workers, Edge functions), then send the response, not the key, to the component. Never ship the key in a client bundle. Browser-safe keys for direct client-side embedding are on the roadmap, not yet available.
|
|
122
126
|
|
|
123
127
|
```ts
|
|
124
|
-
// Server
|
|
128
|
+
// Server side only
|
|
125
129
|
const roxy = createRoxy(process.env.ROXY_API_KEY!);
|
|
126
|
-
|
|
127
|
-
// Browser (widgets auto-mount): publishable key
|
|
128
|
-
<div data-roxy-widget="natal-chart" data-publishable-key="pk_live_xxx" ...></div>
|
|
129
130
|
```
|
|
130
131
|
|
|
131
132
|
### 5. Missing `'use client'` in Next.js App Router
|
|
@@ -190,30 +191,30 @@ import type { NatalChartResponse } from '@roxyapi/sdk';
|
|
|
190
191
|
|
|
191
192
|
### Pattern 1: vanilla HTML, no build step
|
|
192
193
|
|
|
194
|
+
Fetch on your server with the secret key, then inline the response into the component as a child `<script type="application/json" class="roxy-data">`. The component reads it on load. No key in the browser.
|
|
195
|
+
|
|
193
196
|
```html
|
|
194
197
|
<script
|
|
195
198
|
src="https://cdn.jsdelivr.net/npm/@roxyapi/ui@latest/dist/cdn/roxy-ui.js"
|
|
196
199
|
crossorigin="anonymous"
|
|
197
200
|
></script>
|
|
198
201
|
|
|
199
|
-
<roxy-natal-chart
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
const { data } = await roxy.astrology.generateNatalChart({
|
|
205
|
-
body: { date: '1990-01-15', time: '14:30:00', latitude: 19.07, longitude: 72.88, timezone: 5.5 },
|
|
206
|
-
});
|
|
207
|
-
document.getElementById('chart').data = data;
|
|
208
|
-
</script>
|
|
202
|
+
<roxy-natal-chart>
|
|
203
|
+
<script type="application/json" class="roxy-data">
|
|
204
|
+
{ "planets": [ ... ], "houses": [ ... ], "aspects": [ ... ] }
|
|
205
|
+
</script>
|
|
206
|
+
</roxy-natal-chart>
|
|
209
207
|
```
|
|
210
208
|
|
|
211
|
-
|
|
209
|
+
Setting the JavaScript `data` property always wins over the inlined JSON, so the same element also drives dynamic pages.
|
|
210
|
+
|
|
211
|
+
### Pattern 2: React, interactive
|
|
212
|
+
|
|
213
|
+
`<RoxyLocationSearch>` runs in the browser. On select, call your own route, which holds the secret key, and set the returned data on the chart. The key never reaches the client.
|
|
212
214
|
|
|
213
215
|
```tsx
|
|
214
216
|
'use client';
|
|
215
217
|
|
|
216
|
-
import { createRoxy } from '@roxyapi/sdk';
|
|
217
218
|
import {
|
|
218
219
|
RoxyNatalChart,
|
|
219
220
|
RoxyLocationSearch,
|
|
@@ -221,18 +222,18 @@ import {
|
|
|
221
222
|
} from '@roxyapi/ui-react';
|
|
222
223
|
import { useState } from 'react';
|
|
223
224
|
|
|
224
|
-
const roxy = createRoxy(process.env.NEXT_PUBLIC_ROXY_API_KEY!);
|
|
225
|
-
|
|
226
225
|
export function BirthChartView() {
|
|
227
226
|
const [chart, setChart] = useState<RoxyNatalChartProps['data']>(undefined);
|
|
228
227
|
|
|
229
228
|
const onLocationSelect = async (e: CustomEvent<{ latitude?: number; longitude?: number; timezone?: number | string }>) => {
|
|
230
229
|
const { latitude, longitude, timezone } = e.detail;
|
|
231
230
|
if (latitude == null || longitude == null) return;
|
|
232
|
-
|
|
233
|
-
|
|
231
|
+
// Your route calls roxy.astrology.generateNatalChart with the secret key.
|
|
232
|
+
const res = await fetch('/api/natal-chart', {
|
|
233
|
+
method: 'POST',
|
|
234
|
+
body: JSON.stringify({ date: '1990-01-15', time: '14:30:00', latitude, longitude, timezone }),
|
|
234
235
|
});
|
|
235
|
-
setChart(
|
|
236
|
+
setChart(await res.json());
|
|
236
237
|
};
|
|
237
238
|
|
|
238
239
|
return (
|
|
@@ -244,9 +245,11 @@ export function BirthChartView() {
|
|
|
244
245
|
}
|
|
245
246
|
```
|
|
246
247
|
|
|
248
|
+
For a static chart with no picker, fetch in a Server Component and pass `data` to a client component (Pattern 6).
|
|
249
|
+
|
|
247
250
|
### Pattern 3: schema-driven form
|
|
248
251
|
|
|
249
|
-
`<roxy-endpoint-form>` reads the OpenAPI spec and renders the inputs for any endpoint.
|
|
252
|
+
`<roxy-endpoint-form>` reads the OpenAPI spec and renders the inputs for any endpoint. On `roxy-submit`, POST the validated values to your own route, which calls the SDK with the secret key, then set the returned data on the target component.
|
|
250
253
|
|
|
251
254
|
```html
|
|
252
255
|
<roxy-endpoint-form
|
|
@@ -254,41 +257,21 @@ export function BirthChartView() {
|
|
|
254
257
|
method="POST"
|
|
255
258
|
submit-label="Generate kundli"
|
|
256
259
|
></roxy-endpoint-form>
|
|
260
|
+
<roxy-vedic-kundli chart-style="south"></roxy-vedic-kundli>
|
|
257
261
|
|
|
258
262
|
<script type="module">
|
|
259
|
-
import { createRoxy } from 'https://cdn.jsdelivr.net/npm/@roxyapi/sdk@latest/dist/factory.js';
|
|
260
|
-
const roxy = createRoxy('pk_live_xxx');
|
|
261
263
|
const form = document.querySelector('roxy-endpoint-form');
|
|
262
264
|
form.addEventListener('roxy-submit', async (e) => {
|
|
263
|
-
|
|
264
|
-
const
|
|
265
|
-
document.querySelector('roxy-vedic-kundli').data =
|
|
265
|
+
// Your route calls roxy.vedicAstrology.generateBirthChart with the secret key.
|
|
266
|
+
const res = await fetch('/api/kundli', { method: 'POST', body: JSON.stringify(e.detail.values) });
|
|
267
|
+
document.querySelector('roxy-vedic-kundli').data = await res.json();
|
|
266
268
|
});
|
|
267
269
|
</script>
|
|
268
270
|
```
|
|
269
271
|
|
|
270
|
-
### Pattern 4: widgets auto-mount (
|
|
271
|
-
|
|
272
|
-
Use a publishable key (`pk_live_*` or `pk_test_*`) for client-side embeds. Get one at <https://roxyapi.com/account>. Publishable keys are origin-restricted at the API gateway. Register the customer domain (e.g. `https://customer.com`) when creating the key, and the gateway will reject requests from any other origin. Never use a secret key in client-side code (secret keys are unprefixed and live server-side only).
|
|
273
|
-
|
|
274
|
-
```html
|
|
275
|
-
<script
|
|
276
|
-
src="https://cdn.jsdelivr.net/npm/@roxyapi/ui@latest/dist/cdn/widgets.js"
|
|
277
|
-
defer
|
|
278
|
-
></script>
|
|
279
|
-
|
|
280
|
-
<div
|
|
281
|
-
data-roxy-widget="natal-chart"
|
|
282
|
-
data-publishable-key="pk_live_xxx"
|
|
283
|
-
data-date="1990-01-15"
|
|
284
|
-
data-time="14:30:00"
|
|
285
|
-
data-latitude="19.07"
|
|
286
|
-
data-longitude="72.88"
|
|
287
|
-
data-timezone="5.5"
|
|
288
|
-
></div>
|
|
289
|
-
```
|
|
272
|
+
### Pattern 4: widgets auto-mount (coming soon)
|
|
290
273
|
|
|
291
|
-
|
|
274
|
+
A zero-wiring embed that reads `data-*` attributes and renders the matching component is on the roadmap. It needs browser-safe keys, which are not yet available. Until then, use Pattern 1 (inline JSON) for no-build pages.
|
|
292
275
|
|
|
293
276
|
### Pattern 5: MCP tool-call response
|
|
294
277
|
|
|
@@ -392,7 +375,7 @@ Every visible aspect of the chart is driven by `--roxy-*` CSS custom properties
|
|
|
392
375
|
|
|
393
376
|
## Domain ordering
|
|
394
377
|
|
|
395
|
-
When listing domains in user-visible copy, use the canonical order: Western astrology, Vedic astrology, numerology, tarot, biorhythm, I Ching, crystals, dreams, angel numbers. Location is utility, not a selling domain.
|
|
378
|
+
When listing domains in user-visible copy, use the canonical order: Western astrology, Vedic astrology, numerology, tarot, human design, forecast, biorhythm, I Ching, crystals, dreams, angel numbers. Location is utility, not a selling domain.
|
|
396
379
|
|
|
397
380
|
## What not to ship
|
|
398
381
|
|
package/README.md
CHANGED
|
@@ -42,6 +42,14 @@ Light, dark, your brand. Override one CSS variable and every component updates.
|
|
|
42
42
|
<img src="https://raw.githubusercontent.com/RoxyAPI/ui/main/assets/screenshots/vedic-kundli-dark.png" alt="Vedic kundli, dark mode">
|
|
43
43
|
</td>
|
|
44
44
|
</tr>
|
|
45
|
+
<tr>
|
|
46
|
+
<td width="50%" align="center">
|
|
47
|
+
<img src="https://raw.githubusercontent.com/RoxyAPI/ui/main/assets/screenshots/bodygraph-light.png" alt="Human Design bodygraph, light mode">
|
|
48
|
+
</td>
|
|
49
|
+
<td width="50%" align="center">
|
|
50
|
+
<img src="https://raw.githubusercontent.com/RoxyAPI/ui/main/assets/screenshots/bodygraph-dark.png" alt="Human Design bodygraph, dark mode">
|
|
51
|
+
</td>
|
|
52
|
+
</tr>
|
|
45
53
|
</table>
|
|
46
54
|
|
|
47
55
|
```css
|
|
@@ -148,6 +156,25 @@ Every chart, table, and card adapts to light and dark automatically. Hover any i
|
|
|
148
156
|
</tr>
|
|
149
157
|
</table>
|
|
150
158
|
|
|
159
|
+
### Human Design and forecast
|
|
160
|
+
|
|
161
|
+
<table>
|
|
162
|
+
<tr>
|
|
163
|
+
<td width="50%"><strong>Bodygraph</strong> · <code><roxy-bodygraph></code><br><sub>POST /human-design/bodygraph</sub><br>
|
|
164
|
+
<picture>
|
|
165
|
+
<source media="(prefers-color-scheme: dark)" srcset="https://raw.githubusercontent.com/RoxyAPI/ui/main/assets/screenshots/bodygraph-dark.png">
|
|
166
|
+
<img src="https://raw.githubusercontent.com/RoxyAPI/ui/main/assets/screenshots/bodygraph-light.png" alt="Human Design bodygraph with nine centers defined and open, channels between activated gates, plus type, authority, and profile summary">
|
|
167
|
+
</picture>
|
|
168
|
+
</td>
|
|
169
|
+
<td width="50%"><strong>Forecast timeline</strong> · <code><roxy-forecast-timeline></code><br><sub>POST /forecast/timeline</sub><br>
|
|
170
|
+
<picture>
|
|
171
|
+
<source media="(prefers-color-scheme: dark)" srcset="https://raw.githubusercontent.com/RoxyAPI/ui/main/assets/screenshots/forecast-timeline-dark.png">
|
|
172
|
+
<img src="https://raw.githubusercontent.com/RoxyAPI/ui/main/assets/screenshots/forecast-timeline-light.png" alt="Cross-domain forecast timeline of transits, ingresses, retrograde stations, and biorhythm critical days grouped by date and weighted by significance">
|
|
173
|
+
</picture>
|
|
174
|
+
</td>
|
|
175
|
+
</tr>
|
|
176
|
+
</table>
|
|
177
|
+
|
|
151
178
|
### Other domains
|
|
152
179
|
|
|
153
180
|
<table>
|
|
@@ -194,42 +221,24 @@ Tables, cards, forms, and helper components in the [live demo](https://roxyapi.g
|
|
|
194
221
|
|
|
195
222
|
## Start with one component
|
|
196
223
|
|
|
197
|
-
|
|
224
|
+
Fetch with the typed SDK, pass `data` to the component. No glue code.
|
|
198
225
|
|
|
199
|
-
```
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
crossorigin="anonymous"
|
|
203
|
-
defer
|
|
204
|
-
></script>
|
|
205
|
-
<roxy-natal-chart id="chart"></roxy-natal-chart>
|
|
206
|
-
<script type="module">
|
|
207
|
-
import { createRoxy } from 'https://cdn.jsdelivr.net/npm/@roxyapi/sdk@latest/dist/factory.js';
|
|
208
|
-
const roxy = createRoxy('YOUR_API_KEY');
|
|
209
|
-
const { data } = await roxy.astrology.generateNatalChart({
|
|
210
|
-
body: { date: '1990-01-15', time: '14:30:00', latitude: 19.07, longitude: 72.88, timezone: 5.5 },
|
|
211
|
-
});
|
|
212
|
-
document.getElementById('chart').data = data;
|
|
213
|
-
</script>
|
|
214
|
-
```
|
|
226
|
+
```tsx
|
|
227
|
+
import { createRoxy } from '@roxyapi/sdk';
|
|
228
|
+
import { RoxyHoroscopeCard } from '@roxyapi/ui-react';
|
|
215
229
|
|
|
216
|
-
|
|
230
|
+
const roxy = createRoxy(process.env.ROXY_API_KEY!);
|
|
217
231
|
|
|
218
|
-
|
|
232
|
+
const { data } = await roxy.astrology.getDailyHoroscope({ path: { sign: 'aries' } });
|
|
219
233
|
|
|
220
|
-
|
|
221
|
-
<roxy-vedic-kundli id="kundli" chart-style="south"></roxy-vedic-kundli>
|
|
222
|
-
<script type="module">
|
|
223
|
-
import { createRoxy } from 'https://cdn.jsdelivr.net/npm/@roxyapi/sdk@latest/dist/factory.js';
|
|
224
|
-
const roxy = createRoxy('YOUR_API_KEY');
|
|
225
|
-
const { data } = await roxy.vedicAstrology.generateBirthChart({
|
|
226
|
-
body: { date: '1990-01-15', time: '14:30:00', latitude: 19.07, longitude: 72.88, timezone: 5.5 },
|
|
227
|
-
});
|
|
228
|
-
document.getElementById('kundli').data = data;
|
|
229
|
-
</script>
|
|
234
|
+
return <RoxyHoroscopeCard data={data} />;
|
|
230
235
|
```
|
|
231
236
|
|
|
232
|
-
|
|
237
|
+
Then expand into natal charts, kundli, dasha, tarot, and every other domain. The SDK returns `data`, the component renders it; the same pairing holds for all 32 components.
|
|
238
|
+
|
|
239
|
+
> **Pass `data`, not the envelope.** The SDK returns `{ data, error, request, response }`. Pass `data`, or the component renders `[object Object]`. This is the most common integration bug.
|
|
240
|
+
|
|
241
|
+
The key stays on your server. Vanilla HTML or a server-rendered page fetches the same way, then [inlines the JSON into the component](#server-rendered-no-javascript-wiring): no build step, no key in the browser. Try every component in the [live demo](https://roxyapi.github.io/ui/), each with Preview, Code, and shadcn tabs and a live color customizer.
|
|
233
242
|
|
|
234
243
|
## Install
|
|
235
244
|
|
|
@@ -285,7 +294,12 @@ Always call `/location/search` first. Every chart endpoint expects latitude, lon
|
|
|
285
294
|
|
|
286
295
|
Server-rendered and cached pages (WordPress, JSX SSR, static HTML) cannot always run JavaScript to set the `data` property per element. Render the response into a child `<script type="application/json" class="roxy-data">` on the server instead. The component reads it on load. No per-element script, no API key in the browser.
|
|
287
296
|
|
|
297
|
+
Load the bundle once anywhere on the page. It registers every `roxy-*` element, so every component on the page renders from that single tag.
|
|
298
|
+
|
|
288
299
|
```html
|
|
300
|
+
<!-- Once per page: defines every roxy-* element -->
|
|
301
|
+
<script src="https://cdn.jsdelivr.net/npm/@roxyapi/ui@latest/dist/cdn/roxy-ui.js" crossorigin="anonymous" defer></script>
|
|
302
|
+
|
|
289
303
|
<roxy-natal-chart>
|
|
290
304
|
<script type="application/json" class="roxy-data">
|
|
291
305
|
{ "planets": [ ... ], "houses": [ ... ], "aspects": [ ... ] }
|
|
@@ -437,7 +451,48 @@ const { data: cc } = await roxy.tarot.castCelticCross({
|
|
|
437
451
|
<RoxyTarotSpread data={cc} />
|
|
438
452
|
```
|
|
439
453
|
|
|
440
|
-
### 5.
|
|
454
|
+
### 5. Human Design (bodygraph)
|
|
455
|
+
|
|
456
|
+
The breakout 2026 self-knowledge category, computed from the same ephemeris as Western astrology plus the I Ching gate wheel and chakra-style centers. Self-discovery apps, dating and compatibility products, and AI coaching bots ship the full bodygraph first. No coordinates needed; Human Design uses the birth instant, not the observer location.
|
|
457
|
+
|
|
458
|
+
```tsx
|
|
459
|
+
import { RoxyBodygraph } from '@roxyapi/ui-react';
|
|
460
|
+
|
|
461
|
+
// Full bodygraph. The head term every Human Design app leads with ("human design chart").
|
|
462
|
+
// Type, strategy, authority, profile, the nine centers, channels, and every gate
|
|
463
|
+
// activation in one call. Pass the birth instant only, no latitude or longitude.
|
|
464
|
+
const { data: bodygraph } = await roxy.humanDesign.generateBodygraph({
|
|
465
|
+
body: { date: '1990-01-15', time: '14:30:00', timezone: 5.5 },
|
|
466
|
+
});
|
|
467
|
+
<RoxyBodygraph data={bodygraph} />
|
|
468
|
+
```
|
|
469
|
+
|
|
470
|
+
### 6. Forecast (transits, cross-domain timeline)
|
|
471
|
+
|
|
472
|
+
The first cross-domain, stateless forecast in the catalog: one call merges Western transits, Vedic Vimshottari dasha boundaries, and biorhythm critical days into a single significance-scored, time-ordered timeline. Forecast feeds, transit alerts, and timing tools are the buyers. Acquire on the high-volume `astrology transits` search, convert on the cross-domain timeline no competitor ships. No coordinates needed.
|
|
473
|
+
|
|
474
|
+
```tsx
|
|
475
|
+
import { RoxyForecastTimeline } from '@roxyapi/ui-react';
|
|
476
|
+
|
|
477
|
+
// Transit forecast. The demand leader. Western transit-to-natal aspects, sign
|
|
478
|
+
// ingresses, and retrograde stations over the window.
|
|
479
|
+
const { data: transits } = await roxy.forecast.forecastTransits({
|
|
480
|
+
body: { birthData: { date: '1990-01-15', time: '14:30:00', timezone: 5.5 } },
|
|
481
|
+
});
|
|
482
|
+
<RoxyForecastTimeline data={transits} />
|
|
483
|
+
|
|
484
|
+
// Cross-domain timeline. The same window merged with Vedic dasha boundaries and
|
|
485
|
+
// biorhythm critical days into one significance-scored timeline.
|
|
486
|
+
const { data: timeline } = await roxy.forecast.generateTimeline({
|
|
487
|
+
body: {
|
|
488
|
+
birthData: { date: '1990-01-15', time: '14:30:00', timezone: 5.5 },
|
|
489
|
+
domains: ['western', 'vedic', 'biorhythm'],
|
|
490
|
+
},
|
|
491
|
+
});
|
|
492
|
+
<RoxyForecastTimeline data={timeline} />
|
|
493
|
+
```
|
|
494
|
+
|
|
495
|
+
### 7. Biorhythm (daily, forecast)
|
|
441
496
|
|
|
442
497
|
Zero competition domain. Steady search volume with the top Google result being a static calculator page. Pure land-grab for wellness, productivity, sports, and couples apps.
|
|
443
498
|
|
|
@@ -458,7 +513,7 @@ const { data: forecast } = await roxy.biorhythm.getForecast({
|
|
|
458
513
|
<RoxyBiorhythmChart data={forecast} mode="forecast" />
|
|
459
514
|
```
|
|
460
515
|
|
|
461
|
-
###
|
|
516
|
+
### 8. I Ching (cast a reading, hexagram lookup)
|
|
462
517
|
|
|
463
518
|
Meditation apps, decision-making tools, and wisdom chatbots. `i ching API` and `hexagram API` are the keywords.
|
|
464
519
|
|
|
@@ -478,12 +533,13 @@ const { data: random } = await roxy.iching.getRandomHexagram();
|
|
|
478
533
|
|
|
479
534
|
## API keys
|
|
480
535
|
|
|
481
|
-
Get
|
|
536
|
+
Get a key at <https://roxyapi.com/account>.
|
|
537
|
+
|
|
538
|
+
Today every key is a **secret key**: use it server side only (Node, Bun, Hono, Next.js route handlers, Workers). Never commit it, never ship it in a client bundle. Fetch on your server and send the rendered response, not the key, to the browser. The [Start with one component](#start-with-one-component) section and the [framework recipes](#most-used-components-per-domain) show the pattern.
|
|
482
539
|
|
|
483
|
-
|
|
484
|
-
- **Publishable key** (`pk_live_*` / `pk_test_*`). Safe in browsers, locked to the origins you register on the key. Use with the widgets auto-mount script for WordPress, Shopify, static HTML, embed scenarios. The API gateway rejects requests from any origin not on the allowlist.
|
|
540
|
+
Set `ROXY_API_KEY` to your secret key in your server env for every SDK example on this page.
|
|
485
541
|
|
|
486
|
-
|
|
542
|
+
Browser-safe keys for direct client-side embedding are on the roadmap, not yet available. Until they ship, keep the fetch on your server.
|
|
487
543
|
|
|
488
544
|
## Distribution
|
|
489
545
|
|
|
@@ -493,7 +549,7 @@ For the SDK examples on this page, set `ROXY_API_KEY` to a secret key in your se
|
|
|
493
549
|
| npm `@roxyapi/ui-react` | `npmjs.com/package/@roxyapi/ui-react` |
|
|
494
550
|
| jsDelivr CDN (full bundle) | `cdn.jsdelivr.net/npm/@roxyapi/ui@latest/dist/cdn/roxy-ui.js` |
|
|
495
551
|
| jsDelivr CDN (per component) | `cdn.jsdelivr.net/npm/@roxyapi/ui@latest/dist/cdn/components/{name}.js` |
|
|
496
|
-
| Widgets auto-mount | `cdn.jsdelivr.net/npm/@roxyapi/ui@latest/dist/cdn/widgets.js` |
|
|
552
|
+
| Widgets auto-mount (with browser keys, coming soon) | `cdn.jsdelivr.net/npm/@roxyapi/ui@latest/dist/cdn/widgets.js` |
|
|
497
553
|
| shadcn registry | `npx shadcn@latest add https://cdn.jsdelivr.net/gh/RoxyAPI/ui@latest/registry/{name}.json` |
|
|
498
554
|
|
|
499
555
|
## Components
|
|
@@ -526,6 +582,8 @@ For the SDK examples on this page, set `ROXY_API_KEY` to a secret key in your se
|
|
|
526
582
|
| `<roxy-numerology-card>` | Numerology | POST /numerology/{life-path,expression,personal-year,chart} | Life path, expression, personal year, full chart |
|
|
527
583
|
| `<roxy-tarot-card>` | Tarot | GET /tarot/cards/{id}, POST /tarot/daily | Single card with upright and reversed flip |
|
|
528
584
|
| `<roxy-tarot-spread>` | Tarot | POST /tarot/spreads/{three-card,celtic-cross,love}, /tarot/yes-no, /tarot/draw | Spreads with positions and reading |
|
|
585
|
+
| `<roxy-bodygraph>` | Human Design | POST /human-design/bodygraph | Nine-center chart with defined and open centers, active channels, gates, and a type and authority summary |
|
|
586
|
+
| `<roxy-forecast-timeline>` | Forecast | POST /forecast/timeline | Date-grouped events across Western, Vedic, and biorhythm domains, weighted by significance |
|
|
529
587
|
| `<roxy-biorhythm-chart>` | Biorhythm | POST /biorhythm/{daily,forecast,critical-days} | Daily bars, forecast cycle lines, critical days |
|
|
530
588
|
| `<roxy-hexagram>` | I Ching | GET /iching/hexagrams/{number}, /iching/cast, POST /iching/daily, /iching/daily/cast | Hexagram with trigrams, judgment, image, changing lines |
|
|
531
589
|
| `<roxy-endpoint-form>` | Helper | Any endpoint via x-roxy-ui hints | Schema-driven form, emits roxy-submit |
|
|
@@ -565,7 +623,7 @@ roxy-natal-chart {
|
|
|
565
623
|
- Consistent response formats across every domain in the catalog.
|
|
566
624
|
- A11y zero violations enforced in CI.
|
|
567
625
|
- Tight per-component bundle budget enforced in CI.
|
|
568
|
-
- Coverage of the highest-demand endpoints across Western astrology, Vedic astrology, numerology, tarot, biorhythm, I Ching, plus helpers for location search and schema-driven forms.
|
|
626
|
+
- Coverage of the highest-demand endpoints across Western astrology, Vedic astrology, numerology, tarot, Human Design, forecast, biorhythm, I Ching, plus helpers for location search and schema-driven forms.
|
|
569
627
|
|
|
570
628
|
## Built for AI agents
|
|
571
629
|
|
|
@@ -741,7 +799,7 @@ Components ship in Shadow DOM for style isolation; Tailwind utilities are scoped
|
|
|
741
799
|
<details>
|
|
742
800
|
<summary><strong>What is the security model for API keys?</strong></summary>
|
|
743
801
|
|
|
744
|
-
|
|
802
|
+
Today keys are secret keys: they live server side only and grant full access, so never ship one in a client bundle. Fetch on your server and pass the rendered response, not the key, to the browser. Browser-safe keys with an origin allowlist for direct client-side embedding are on the roadmap and not yet available.
|
|
745
803
|
|
|
746
804
|
For CSP, allow `script-src https://cdn.jsdelivr.net` if loading the bundle from the CDN. Subresource Integrity hashes are available via the jsDelivr SRI API for any pinned version.
|
|
747
805
|
</details>
|
|
@@ -752,11 +810,11 @@ For CSP, allow `script-src https://cdn.jsdelivr.net` if loading the bundle from
|
|
|
752
810
|
Semver. Pre-1.0, minor bumps may include breaking changes (we will note them in the changelog). Patch bumps are always backwards-compatible. Pin a concrete version in production code:
|
|
753
811
|
|
|
754
812
|
```bash
|
|
755
|
-
npm install @roxyapi/ui@0.
|
|
813
|
+
npm install @roxyapi/ui@0.8.x
|
|
756
814
|
```
|
|
757
815
|
|
|
758
816
|
```html
|
|
759
|
-
<script src="https://cdn.jsdelivr.net/npm/@roxyapi/ui@0.
|
|
817
|
+
<script src="https://cdn.jsdelivr.net/npm/@roxyapi/ui@0.8.0/dist/cdn/roxy-ui.js"></script>
|
|
760
818
|
```
|
|
761
819
|
|
|
762
820
|
The `@latest` URL on this page is for paste-friendly marketing; production code should pin.
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
"use strict";var RoxyUI_bodygraph=(()=>{var j=Object.defineProperty;var fe=Object.getOwnPropertyDescriptor;var qe=Object.getOwnPropertyNames;var Ve=Object.prototype.hasOwnProperty;var Ye=(s,e)=>{for(var t in e)j(s,t,{get:e[t],enumerable:!0})},We=(s,e,t,r)=>{if(e&&typeof e=="object"||typeof e=="function")for(let n of qe(e))!Ve.call(s,n)&&n!==t&&j(s,n,{get:()=>e[n],enumerable:!(r=fe(e,n))||r.enumerable});return s};var Ke=s=>We(j({},"__esModule",{value:!0}),s),Z=(s,e,t,r)=>{for(var n=r>1?void 0:r?fe(e,t):e,o=s.length-1,i;o>=0;o--)(i=s[o])&&(n=(r?i(e,t,n):i(n))||n);return r&&n&&j(e,t,n),n};var Ct={};Ye(Ct,{RoxyBodygraph:()=>w});var G=globalThis,D=G.ShadowRoot&&(G.ShadyCSS===void 0||G.ShadyCSS.nativeShadow)&&"adoptedStyleSheets"in Document.prototype&&"replace"in CSSStyleSheet.prototype,Q=Symbol(),ye=new WeakMap,R=class{constructor(e,t,r){if(this._$cssResult$=!0,r!==Q)throw Error("CSSResult is not constructable. Use `unsafeCSS` or `css` instead.");this.cssText=e,this.t=t}get styleSheet(){let e=this.o,t=this.t;if(D&&e===void 0){let r=t!==void 0&&t.length===1;r&&(e=ye.get(t)),e===void 0&&((this.o=e=new CSSStyleSheet).replaceSync(this.cssText),r&&ye.set(t,e))}return e}toString(){return this.cssText}},be=s=>new R(typeof s=="string"?s:s+"",void 0,Q),T=(s,...e)=>{let t=s.length===1?s[0]:e.reduce((r,n,o)=>r+(i=>{if(i._$cssResult$===!0)return i.cssText;if(typeof i=="number")return i;throw Error("Value passed to 'css' function must be a 'css' function result: "+i+". Use 'unsafeCSS' to pass non-literal values, but take care to ensure page security.")})(n)+s[o+1],s[0]);return new R(t,s,Q)},xe=(s,e)=>{if(D)s.adoptedStyleSheets=e.map(t=>t instanceof CSSStyleSheet?t:t.styleSheet);else for(let t of e){let r=document.createElement("style"),n=G.litNonce;n!==void 0&&r.setAttribute("nonce",n),r.textContent=t.cssText,s.appendChild(r)}},ee=D?s=>s:s=>s instanceof CSSStyleSheet?(e=>{let t="";for(let r of e.cssRules)t+=r.cssText;return be(t)})(s):s;var{is:Je,defineProperty:Xe,getOwnPropertyDescriptor:Fe,getOwnPropertyNames:Ze,getOwnPropertySymbols:Qe,getPrototypeOf:et}=Object,z=globalThis,$e=z.trustedTypes,tt=$e?$e.emptyScript:"",rt=z.reactiveElementPolyfillSupport,N=(s,e)=>s,O={toAttribute(s,e){switch(e){case Boolean:s=s?tt:null;break;case Object:case Array:s=s==null?s:JSON.stringify(s)}return s},fromAttribute(s,e){let t=s;switch(e){case Boolean:t=s!==null;break;case Number:t=s===null?null:Number(s);break;case Object:case Array:try{t=JSON.parse(s)}catch{t=null}}return t}},q=(s,e)=>!Je(s,e),ve={attribute:!0,type:String,converter:O,reflect:!1,useDefault:!1,hasChanged:q};Symbol.metadata??=Symbol("metadata"),z.litPropertyMetadata??=new WeakMap;var y=class extends HTMLElement{static addInitializer(e){this._$Ei(),(this.l??=[]).push(e)}static get observedAttributes(){return this.finalize(),this._$Eh&&[...this._$Eh.keys()]}static createProperty(e,t=ve){if(t.state&&(t.attribute=!1),this._$Ei(),this.prototype.hasOwnProperty(e)&&((t=Object.create(t)).wrapped=!0),this.elementProperties.set(e,t),!t.noAccessor){let r=Symbol(),n=this.getPropertyDescriptor(e,r,t);n!==void 0&&Xe(this.prototype,e,n)}}static getPropertyDescriptor(e,t,r){let{get:n,set:o}=Fe(this.prototype,e)??{get(){return this[t]},set(i){this[t]=i}};return{get:n,set(i){let a=n?.call(this);o?.call(this,i),this.requestUpdate(e,a,r)},configurable:!0,enumerable:!0}}static getPropertyOptions(e){return this.elementProperties.get(e)??ve}static _$Ei(){if(this.hasOwnProperty(N("elementProperties")))return;let e=et(this);e.finalize(),e.l!==void 0&&(this.l=[...e.l]),this.elementProperties=new Map(e.elementProperties)}static finalize(){if(this.hasOwnProperty(N("finalized")))return;if(this.finalized=!0,this._$Ei(),this.hasOwnProperty(N("properties"))){let t=this.properties,r=[...Ze(t),...Qe(t)];for(let n of r)this.createProperty(n,t[n])}let e=this[Symbol.metadata];if(e!==null){let t=litPropertyMetadata.get(e);if(t!==void 0)for(let[r,n]of t)this.elementProperties.set(r,n)}this._$Eh=new Map;for(let[t,r]of this.elementProperties){let n=this._$Eu(t,r);n!==void 0&&this._$Eh.set(n,t)}this.elementStyles=this.finalizeStyles(this.styles)}static finalizeStyles(e){let t=[];if(Array.isArray(e)){let r=new Set(e.flat(1/0).reverse());for(let n of r)t.unshift(ee(n))}else e!==void 0&&t.push(ee(e));return t}static _$Eu(e,t){let r=t.attribute;return r===!1?void 0:typeof r=="string"?r:typeof e=="string"?e.toLowerCase():void 0}constructor(){super(),this._$Ep=void 0,this.isUpdatePending=!1,this.hasUpdated=!1,this._$Em=null,this._$Ev()}_$Ev(){this._$ES=new Promise(e=>this.enableUpdating=e),this._$AL=new Map,this._$E_(),this.requestUpdate(),this.constructor.l?.forEach(e=>e(this))}addController(e){(this._$EO??=new Set).add(e),this.renderRoot!==void 0&&this.isConnected&&e.hostConnected?.()}removeController(e){this._$EO?.delete(e)}_$E_(){let e=new Map,t=this.constructor.elementProperties;for(let r of t.keys())this.hasOwnProperty(r)&&(e.set(r,this[r]),delete this[r]);e.size>0&&(this._$Ep=e)}createRenderRoot(){let e=this.shadowRoot??this.attachShadow(this.constructor.shadowRootOptions);return xe(e,this.constructor.elementStyles),e}connectedCallback(){this.renderRoot??=this.createRenderRoot(),this.enableUpdating(!0),this._$EO?.forEach(e=>e.hostConnected?.())}enableUpdating(e){}disconnectedCallback(){this._$EO?.forEach(e=>e.hostDisconnected?.())}attributeChangedCallback(e,t,r){this._$AK(e,r)}_$ET(e,t){let r=this.constructor.elementProperties.get(e),n=this.constructor._$Eu(e,r);if(n!==void 0&&r.reflect===!0){let o=(r.converter?.toAttribute!==void 0?r.converter:O).toAttribute(t,r.type);this._$Em=e,o==null?this.removeAttribute(n):this.setAttribute(n,o),this._$Em=null}}_$AK(e,t){let r=this.constructor,n=r._$Eh.get(e);if(n!==void 0&&this._$Em!==n){let o=r.getPropertyOptions(n),i=typeof o.converter=="function"?{fromAttribute:o.converter}:o.converter?.fromAttribute!==void 0?o.converter:O;this._$Em=n;let a=i.fromAttribute(t,o.type);this[n]=a??this._$Ej?.get(n)??a,this._$Em=null}}requestUpdate(e,t,r,n=!1,o){if(e!==void 0){let i=this.constructor;if(n===!1&&(o=this[e]),r??=i.getPropertyOptions(e),!((r.hasChanged??q)(o,t)||r.useDefault&&r.reflect&&o===this._$Ej?.get(e)&&!this.hasAttribute(i._$Eu(e,r))))return;this.C(e,t,r)}this.isUpdatePending===!1&&(this._$ES=this._$EP())}C(e,t,{useDefault:r,reflect:n,wrapped:o},i){r&&!(this._$Ej??=new Map).has(e)&&(this._$Ej.set(e,i??t??this[e]),o!==!0||i!==void 0)||(this._$AL.has(e)||(this.hasUpdated||r||(t=void 0),this._$AL.set(e,t)),n===!0&&this._$Em!==e&&(this._$Eq??=new Set).add(e))}async _$EP(){this.isUpdatePending=!0;try{await this._$ES}catch(t){Promise.reject(t)}let e=this.scheduleUpdate();return e!=null&&await e,!this.isUpdatePending}scheduleUpdate(){return this.performUpdate()}performUpdate(){if(!this.isUpdatePending)return;if(!this.hasUpdated){if(this.renderRoot??=this.createRenderRoot(),this._$Ep){for(let[n,o]of this._$Ep)this[n]=o;this._$Ep=void 0}let r=this.constructor.elementProperties;if(r.size>0)for(let[n,o]of r){let{wrapped:i}=o,a=this[n];i!==!0||this._$AL.has(n)||a===void 0||this.C(n,void 0,o,a)}}let e=!1,t=this._$AL;try{e=this.shouldUpdate(t),e?(this.willUpdate(t),this._$EO?.forEach(r=>r.hostUpdate?.()),this.update(t)):this._$EM()}catch(r){throw e=!1,this._$EM(),r}e&&this._$AE(t)}willUpdate(e){}_$AE(e){this._$EO?.forEach(t=>t.hostUpdated?.()),this.hasUpdated||(this.hasUpdated=!0,this.firstUpdated(e)),this.updated(e)}_$EM(){this._$AL=new Map,this.isUpdatePending=!1}get updateComplete(){return this.getUpdateComplete()}getUpdateComplete(){return this._$ES}shouldUpdate(e){return!0}update(e){this._$Eq&&=this._$Eq.forEach(t=>this._$ET(t,this[t])),this._$EM()}updated(e){}firstUpdated(e){}};y.elementStyles=[],y.shadowRootOptions={mode:"open"},y[N("elementProperties")]=new Map,y[N("finalized")]=new Map,rt?.({ReactiveElement:y}),(z.reactiveElementVersions??=[]).push("2.1.2");var ae=globalThis,Ae=s=>s,V=ae.trustedTypes,_e=V?V.createPolicy("lit-html",{createHTML:s=>s}):void 0,Re="$lit$",x=`lit$${Math.random().toFixed(9).slice(2)}$`,Te="?"+x,st=`<${Te}>`,_=document,k=()=>_.createComment(""),H=s=>s===null||typeof s!="object"&&typeof s!="function",le=Array.isArray,nt=s=>le(s)||typeof s?.[Symbol.iterator]=="function",te=`[
|
|
2
|
+
\f\r]`,M=/<(?:(!--|\/[^a-zA-Z])|(\/?[a-zA-Z][^>\s]*)|(\/?$))/g,Se=/-->/g,Ee=/>/g,v=RegExp(`>|${te}(?:([^\\s"'>=/]+)(${te}*=${te}*(?:[^
|
|
3
|
+
\f\r"'\`<>=]|("|')|))|$)`,"g"),we=/'/g,Ce=/"/g,Ne=/^(?:script|style|textarea|title)$/i,ce=s=>(e,...t)=>({_$litType$:s,strings:e,values:t}),m=ce(1),g=ce(2),Mt=ce(3),S=Symbol.for("lit-noChange"),c=Symbol.for("lit-nothing"),Pe=new WeakMap,A=_.createTreeWalker(_,129);function Oe(s,e){if(!le(s)||!s.hasOwnProperty("raw"))throw Error("invalid template strings array");return _e!==void 0?_e.createHTML(e):e}var ot=(s,e)=>{let t=s.length-1,r=[],n,o=e===2?"<svg>":e===3?"<math>":"",i=M;for(let a=0;a<t;a++){let l=s[a],p,h,d=-1,f=0;for(;f<l.length&&(i.lastIndex=f,h=i.exec(l),h!==null);)f=i.lastIndex,i===M?h[1]==="!--"?i=Se:h[1]!==void 0?i=Ee:h[2]!==void 0?(Ne.test(h[2])&&(n=RegExp("</"+h[2],"g")),i=v):h[3]!==void 0&&(i=v):i===v?h[0]===">"?(i=n??M,d=-1):h[1]===void 0?d=-2:(d=i.lastIndex-h[2].length,p=h[1],i=h[3]===void 0?v:h[3]==='"'?Ce:we):i===Ce||i===we?i=v:i===Se||i===Ee?i=M:(i=v,n=void 0);let b=i===v&&s[a+1].startsWith("/>")?" ":"";o+=i===M?l+st:d>=0?(r.push(p),l.slice(0,d)+Re+l.slice(d)+x+b):l+x+(d===-2?a:b)}return[Oe(s,o+(s[t]||"<?>")+(e===2?"</svg>":e===3?"</math>":"")),r]},L=class s{constructor({strings:e,_$litType$:t},r){let n;this.parts=[];let o=0,i=0,a=e.length-1,l=this.parts,[p,h]=ot(e,t);if(this.el=s.createElement(p,r),A.currentNode=this.el.content,t===2||t===3){let d=this.el.content.firstChild;d.replaceWith(...d.childNodes)}for(;(n=A.nextNode())!==null&&l.length<a;){if(n.nodeType===1){if(n.hasAttributes())for(let d of n.getAttributeNames())if(d.endsWith(Re)){let f=h[i++],b=n.getAttribute(d).split(x),B=/([.?@])?(.*)/.exec(f);l.push({type:1,index:o,name:B[2],strings:b,ctor:B[1]==="."?se:B[1]==="?"?ne:B[1]==="@"?oe:P}),n.removeAttribute(d)}else d.startsWith(x)&&(l.push({type:6,index:o}),n.removeAttribute(d));if(Ne.test(n.tagName)){let d=n.textContent.split(x),f=d.length-1;if(f>0){n.textContent=V?V.emptyScript:"";for(let b=0;b<f;b++)n.append(d[b],k()),A.nextNode(),l.push({type:2,index:++o});n.append(d[f],k())}}}else if(n.nodeType===8)if(n.data===Te)l.push({type:2,index:o});else{let d=-1;for(;(d=n.data.indexOf(x,d+1))!==-1;)l.push({type:7,index:o}),d+=x.length-1}o++}}static createElement(e,t){let r=_.createElement("template");return r.innerHTML=e,r}};function C(s,e,t=s,r){if(e===S)return e;let n=r!==void 0?t._$Co?.[r]:t._$Cl,o=H(e)?void 0:e._$litDirective$;return n?.constructor!==o&&(n?._$AO?.(!1),o===void 0?n=void 0:(n=new o(s),n._$AT(s,t,r)),r!==void 0?(t._$Co??=[])[r]=n:t._$Cl=n),n!==void 0&&(e=C(s,n._$AS(s,e.values),n,r)),e}var re=class{constructor(e,t){this._$AV=[],this._$AN=void 0,this._$AD=e,this._$AM=t}get parentNode(){return this._$AM.parentNode}get _$AU(){return this._$AM._$AU}u(e){let{el:{content:t},parts:r}=this._$AD,n=(e?.creationScope??_).importNode(t,!0);A.currentNode=n;let o=A.nextNode(),i=0,a=0,l=r[0];for(;l!==void 0;){if(i===l.index){let p;l.type===2?p=new U(o,o.nextSibling,this,e):l.type===1?p=new l.ctor(o,l.name,l.strings,this,e):l.type===6&&(p=new ie(o,this,e)),this._$AV.push(p),l=r[++a]}i!==l?.index&&(o=A.nextNode(),i++)}return A.currentNode=_,n}p(e){let t=0;for(let r of this._$AV)r!==void 0&&(r.strings!==void 0?(r._$AI(e,r,t),t+=r.strings.length-2):r._$AI(e[t])),t++}},U=class s{get _$AU(){return this._$AM?._$AU??this._$Cv}constructor(e,t,r,n){this.type=2,this._$AH=c,this._$AN=void 0,this._$AA=e,this._$AB=t,this._$AM=r,this.options=n,this._$Cv=n?.isConnected??!0}get parentNode(){let e=this._$AA.parentNode,t=this._$AM;return t!==void 0&&e?.nodeType===11&&(e=t.parentNode),e}get startNode(){return this._$AA}get endNode(){return this._$AB}_$AI(e,t=this){e=C(this,e,t),H(e)?e===c||e==null||e===""?(this._$AH!==c&&this._$AR(),this._$AH=c):e!==this._$AH&&e!==S&&this._(e):e._$litType$!==void 0?this.$(e):e.nodeType!==void 0?this.T(e):nt(e)?this.k(e):this._(e)}O(e){return this._$AA.parentNode.insertBefore(e,this._$AB)}T(e){this._$AH!==e&&(this._$AR(),this._$AH=this.O(e))}_(e){this._$AH!==c&&H(this._$AH)?this._$AA.nextSibling.data=e:this.T(_.createTextNode(e)),this._$AH=e}$(e){let{values:t,_$litType$:r}=e,n=typeof r=="number"?this._$AC(e):(r.el===void 0&&(r.el=L.createElement(Oe(r.h,r.h[0]),this.options)),r);if(this._$AH?._$AD===n)this._$AH.p(t);else{let o=new re(n,this),i=o.u(this.options);o.p(t),this.T(i),this._$AH=o}}_$AC(e){let t=Pe.get(e.strings);return t===void 0&&Pe.set(e.strings,t=new L(e)),t}k(e){le(this._$AH)||(this._$AH=[],this._$AR());let t=this._$AH,r,n=0;for(let o of e)n===t.length?t.push(r=new s(this.O(k()),this.O(k()),this,this.options)):r=t[n],r._$AI(o),n++;n<t.length&&(this._$AR(r&&r._$AB.nextSibling,n),t.length=n)}_$AR(e=this._$AA.nextSibling,t){for(this._$AP?.(!1,!0,t);e!==this._$AB;){let r=Ae(e).nextSibling;Ae(e).remove(),e=r}}setConnected(e){this._$AM===void 0&&(this._$Cv=e,this._$AP?.(e))}},P=class{get tagName(){return this.element.tagName}get _$AU(){return this._$AM._$AU}constructor(e,t,r,n,o){this.type=1,this._$AH=c,this._$AN=void 0,this.element=e,this.name=t,this._$AM=n,this.options=o,r.length>2||r[0]!==""||r[1]!==""?(this._$AH=Array(r.length-1).fill(new String),this.strings=r):this._$AH=c}_$AI(e,t=this,r,n){let o=this.strings,i=!1;if(o===void 0)e=C(this,e,t,0),i=!H(e)||e!==this._$AH&&e!==S,i&&(this._$AH=e);else{let a=e,l,p;for(e=o[0],l=0;l<o.length-1;l++)p=C(this,a[r+l],t,l),p===S&&(p=this._$AH[l]),i||=!H(p)||p!==this._$AH[l],p===c?e=c:e!==c&&(e+=(p??"")+o[l+1]),this._$AH[l]=p}i&&!n&&this.j(e)}j(e){e===c?this.element.removeAttribute(this.name):this.element.setAttribute(this.name,e??"")}},se=class extends P{constructor(){super(...arguments),this.type=3}j(e){this.element[this.name]=e===c?void 0:e}},ne=class extends P{constructor(){super(...arguments),this.type=4}j(e){this.element.toggleAttribute(this.name,!!e&&e!==c)}},oe=class extends P{constructor(e,t,r,n,o){super(e,t,r,n,o),this.type=5}_$AI(e,t=this){if((e=C(this,e,t,0)??c)===S)return;let r=this._$AH,n=e===c&&r!==c||e.capture!==r.capture||e.once!==r.once||e.passive!==r.passive,o=e!==c&&(r===c||n);n&&this.element.removeEventListener(this.name,this,r),o&&this.element.addEventListener(this.name,this,e),this._$AH=e}handleEvent(e){typeof this._$AH=="function"?this._$AH.call(this.options?.host??this.element,e):this._$AH.handleEvent(e)}},ie=class{constructor(e,t,r){this.element=e,this.type=6,this._$AN=void 0,this._$AM=t,this.options=r}get _$AU(){return this._$AM._$AU}_$AI(e){C(this,e)}};var it=ae.litHtmlPolyfillSupport;it?.(L,U),(ae.litHtmlVersions??=[]).push("3.3.2");var Me=(s,e,t)=>{let r=t?.renderBefore??e,n=r._$litPart$;if(n===void 0){let o=t?.renderBefore??null;r._$litPart$=n=new U(e.insertBefore(k(),o),o,void 0,t??{})}return n._$AI(s),n};var de=globalThis,$=class extends y{constructor(){super(...arguments),this.renderOptions={host:this},this._$Do=void 0}createRenderRoot(){let e=super.createRenderRoot();return this.renderOptions.renderBefore??=e.firstChild,e}update(e){let t=this.render();this.hasUpdated||(this.renderOptions.isConnected=this.isConnected),super.update(e),this._$Do=Me(t,this.renderRoot,this.renderOptions)}connectedCallback(){super.connectedCallback(),this._$Do?.setConnected(!0)}disconnectedCallback(){super.disconnectedCallback(),this._$Do?.setConnected(!1)}render(){return S}};$._$litElement$=!0,$.finalized=!0,de.litElementHydrateSupport?.({LitElement:$});var at=de.litElementPolyfillSupport;at?.({LitElement:$});(de.litElementVersions??=[]).push("4.2.2");var ke=s=>(e,t)=>{t!==void 0?t.addInitializer(()=>{customElements.define(s,e)}):customElements.define(s,e)};var lt={attribute:!0,type:String,converter:O,reflect:!1,hasChanged:q},ct=(s=lt,e,t)=>{let{kind:r,metadata:n}=t,o=globalThis.litPropertyMetadata.get(n);if(o===void 0&&globalThis.litPropertyMetadata.set(n,o=new Map),r==="setter"&&((s=Object.create(s)).wrapped=!0),o.set(t.name,s),r==="accessor"){let{name:i}=t;return{set(a){let l=e.get.call(this);e.set.call(this,a),this.requestUpdate(i,l,s,!0,a)},init(a){return a!==void 0&&this.C(i,void 0,s,a),a}}}if(r==="setter"){let{name:i}=t;return function(a){let l=this[i];e.call(this,a),this.requestUpdate(i,l,s,!0,a)}}throw Error("Unsupported decorator location: "+r)};function pe(s){return(e,t)=>typeof t=="object"?ct(s,e,t):((r,n,o)=>{let i=n.hasOwnProperty(o);return n.constructor.createProperty(o,r),i?Object.getOwnPropertyDescriptor(n,o):void 0})(s,e,t)}var He={Sun:"\u2609",Moon:"\u263D",Mercury:"\u263F",Venus:"\u2640",Earth:"\u2641",Mars:"\u2642",Jupiter:"\u2643",Saturn:"\u2644",Uranus:"\u2645",Neptune:"\u2646",Pluto:"\u2647",Rahu:"\u260A",Ketu:"\u260B",Ascendant:"Asc",Lagna:"La",NorthNode:"\u260A",SouthNode:"\u260B","North node":"\u260A","South node":"\u260B",Chiron:"\u26B7",Lilith:"\u26B8","Black moon lilith":"\u26B8"};var dt=["Aries","Taurus","Gemini","Cancer","Leo","Virgo","Libra","Scorpio","Sagittarius","Capricorn","Aquarius","Pisces"],xr=dt.map(s=>s.toLowerCase());var Le=T`:host{font-family:var(--roxy-font-sans,system-ui, -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif);color:var(--roxy-fg,#0a0a0a);font-size:var(--roxy-text-base,1rem);line-height:var(--roxy-leading-normal,1.5);animation:roxy-fade-in var(--roxy-motion-duration,.2s) var(--roxy-motion-easing,cubic-bezier(.4, 0, .2, 1)) both;background:0 0;display:block;container-type:inline-size}*,:before,:after{box-sizing:border-box}@keyframes roxy-fade-in{0%{opacity:0;transform:translateY(2px)}to{opacity:1;transform:translateY(0)}}@media (prefers-reduced-motion:reduce){:host{animation:none}}.roxy-skeleton{background:linear-gradient(90deg, var(--roxy-border,#e4e4e7) 0%, color-mix(in srgb, var(--roxy-border,#e4e4e7) 60%, transparent) 50%, var(--roxy-border,#e4e4e7) 100%);border-radius:var(--roxy-radius-md,8px);background-size:200% 100%;animation:1.4s ease-in-out infinite roxy-shimmer}@keyframes roxy-shimmer{0%{background-position:200% 0}to{background-position:-200% 0}}@media (prefers-reduced-motion:reduce){.roxy-skeleton{animation:none}}.roxy-empty{padding:var(--roxy-space-lg,1.5rem);color:var(--roxy-muted,#71717a);text-align:center;font-size:var(--roxy-text-sm,.875rem)}:host(:focus-within) .roxy-card{outline:2px solid var(--roxy-ring,#f59e0b66);outline-offset:2px}:host{font-variant-emoji:text}`;var J=4,X=9,Ie=(100+2*X)*J,pt=(100+2*X)*J;function u(s,e){return{x:(s+X)*J,y:(e+X)*J}}var I=50,ge=s=>2*I-s,he={head:{64:[45.5,11.2],61:[50,11.2],63:[54.5,11.2]},ajna:{47:[45.3,18],24:[50,18],4:[54.7,18],17:[45.6,20.6],11:[54.4,20.6],43:[50,25.3]},throat:{62:[45.5,32.3],23:[50,32.3],56:[54.5,32.3],16:[42,34.6],35:[58,34.6],12:[58,37.6],20:[42,40.6],45:[58,40.6],31:[46,42.4],8:[50,42.4],33:[54,42.4]},g:{1:[50,47.5],7:[45.6,50.3],13:[54.4,50.3],10:[40,53.3],25:[60,53.3],15:[45.6,56.6],46:[54.4,56.6],2:[50,59]},heart:{21:[62.5,58.5],51:[62.5,61.3],26:[62.5,64.1],40:[73,61.3]},spleen:{48:[20,70.6],57:[24,72.3],44:[28,74],50:[32,75.6],32:[28,77.2],28:[24,78.9],18:[20,80.6]},sacral:{5:[45.5,72.5],14:[50,72.5],29:[54.5,72.5],34:[42,75.6],27:[42,79],59:[58,79],42:[45.5,81.4],3:[50,81.4],9:[54.5,81.4]},"solar-plexus":{},root:{53:[45.5,89.9],60:[50,89.9],52:[54.5,89.9],54:[42,92.7],19:[58,92.7],38:[42,95.3],39:[58,95.3],58:[42,98],41:[58,98]}},ht={48:36,57:22,44:37,50:6,32:49,28:55,18:30};function ut(){let s={},e={};for(let[t,[r,n]]of Object.entries(he.spleen))he["solar-plexus"][ht[Number(t)]]=[ge(r),n];for(let[t,r]of Object.entries(he))for(let[n,[o,i]]of Object.entries(r))s[Number(n)]=u(o,i),e[Number(n)]=t;return{points:s,centerOf:e}}var{points:me,centerOf:Sr}=ut(),Er=Ie/2;function E(s){return s.map(([e,t])=>u(e,t))}function ue(s,e,t){return E([[I-s,e],[I+s,e],[I+s,t],[I-s,t]])}var Ue=[[18.4,68],[18.4,81.8],[34.7,74.9]],mt=[{id:"head",label:"Head",color:"gold",points:E([[40,14.3],[60,14.3],[50,6]]),labelAnchor:u(63,9),labelAlign:"start"},{id:"ajna",label:"Ajna",color:"green",points:E([[40,15.6],[60,15.6],[50,27.6]]),labelAnchor:u(62,21),labelAlign:"start"},{id:"throat",label:"Throat",color:"brown",points:ue(9.5,30.4,43.6),labelAnchor:u(83,34),labelAlign:"start"},{id:"g",label:"G",color:"gold",points:E([[50,45],[60.7,53.3],[50,61.6],[39.3,53.3]]),labelAnchor:u(13,51),labelAlign:"end"},{id:"heart",label:"Heart",color:"red",points:E([[61.5,57],[76.5,61.3],[61.5,65.6]]),labelAnchor:u(85,56),labelAlign:"start"},{id:"spleen",label:"Spleen",color:"brown",points:E(Ue),labelAnchor:u(13,70),labelAlign:"end"},{id:"sacral",label:"Sacral",color:"red",points:ue(9.5,70.6,83.6),labelAnchor:u(85,88),labelAlign:"start"},{id:"solar-plexus",label:"Solar Plexus",color:"brown",points:E(Ue.map(([s,e])=>[ge(s),e])),labelAnchor:u(87,73),labelAlign:"start"},{id:"root",label:"Root",color:"brown",points:ue(9.5,87.9,99.9),labelAnchor:u(50,103),labelAlign:"middle"}],gt=[[64,47],[61,24],[63,4],[17,62],[11,56],[43,23],[16,48],[20,34],[20,10],[7,31],[1,8],[13,33],[21,45],[12,22],[35,36],[57,20],[15,5],[2,14],[46,29],[34,10],[10,57],[25,51],[27,50],[57,34],[26,44],[18,58],[28,38],[32,54],[3,60],[9,52],[42,53],[59,6],[19,49],[39,55],[41,30],[37,40]],ft=yt();function yt(){let s=ge,e=[[50,-2],[60,-2],[60.5,9],[57,18],[56,21],[54,24],[52,27],[54,28],[64,30],[80,34],[83.5,40],[84,56],[83,74],[82,84],[76,92],[68,97],[64,99],[62,100],[60,100]],t=[`M ${W(e[0])}`];for(let r=1;r+2<e.length;r+=3)t.push(`C ${W(e[r])} ${W(e[r+1])} ${W(e[r+2])}`);t.push(`L ${K(e[e.length-1],s)}`);for(let r=e.length-3;r>=1;r-=3)t.push(`C ${K(e[r+1],s)} ${K(e[r],s)} ${K(e[r-1],s)}`);return t.push("Z"),t.join(" ")}function W([s,e]){let t=u(s,e);return`${t.x} ${t.y}`}function K([s,e],t){let r=u(t(s),e);return`${r.x} ${r.y}`}function bt(s){return s.map(e=>`${e.x},${e.y}`).join(" ")}function Be(s,e){return s<e?`${s}-${e}`:`${e}-${s}`}function xt(){return g`<path class="bg-body" d=${ft} />`}function $t(s,e){let t=[];for(let[r,n]of gt){let o=me[r],i=me[n];if(!o||!i)continue;if(t.push(g`<line class="bg-channel" x1=${o.x} y1=${o.y} x2=${i.x} y2=${i.y} />`),s.has(Be(r,n))){t.push(g`<line class="bg-channel on" x1=${o.x} y1=${o.y} x2=${i.x} y2=${i.y} />`);continue}let a={x:(o.x+i.x)/2,y:(o.y+i.y)/2};e.has(r)&&t.push(g`<line class="bg-half" x1=${o.x} y1=${o.y} x2=${a.x} y2=${a.y} />`),e.has(n)&&t.push(g`<line class="bg-half" x1=${i.x} y1=${i.y} x2=${a.x} y2=${a.y} />`)}return t}function vt(s,e,t){let r=t.x-e.x,n=t.y-e.y,o=r*r+n*n;if(o===0)return e;let i=Math.max(0,Math.min(1,((s.x-e.x)*r+(s.y-e.y)*n)/o));return{x:e.x+i*r,y:e.y+i*n}}function At(s,e){let t=e[0],r=Number.POSITIVE_INFINITY;for(let n=0;n<e.length;n++){let o=vt(s,e[n],e[(n+1)%e.length]),i=(o.x-s.x)**2+(o.y-s.y)**2;i<r&&(r=i,t=o)}return t}function _t(s){return mt.map(e=>{let t=s.has(e.id),r=`bg-center bg-${e.color}${t?" defined":""}`,n=At(e.labelAnchor,e.points);return g`<g>
|
|
4
|
+
<line class="bg-leader" x1=${e.labelAnchor.x} y1=${e.labelAnchor.y} x2=${n.x} y2=${n.y} />
|
|
5
|
+
<polygon class=${r} points=${bt(e.points)}><title>${e.label}: ${t?"defined":"open"}</title></polygon>
|
|
6
|
+
<text class="bg-center-label" x=${e.labelAnchor.x} y=${e.labelAnchor.y} text-anchor=${e.labelAlign} dominant-baseline="central">${e.label}</text>
|
|
7
|
+
</g>`})}function St(s,e){let t=[];for(let[r,n]of Object.entries(me)){let o=Number(r);if(!s.has(o))continue;let i=e.get(o);t.push(g`<text class="bg-gate" x=${n.x} y=${n.y} text-anchor="middle" dominant-baseline="central">${o}${i?g`<title>${i}</title>`:c}</text>`)}return t}function je(s,e){return Be(s,e)}var Ge=`0 0 ${Ie} ${pt}`;function De(s){return g`
|
|
8
|
+
${xt()}
|
|
9
|
+
${$t(s.activeChannels,s.activeGates)}
|
|
10
|
+
${_t(s.definedCenters)}
|
|
11
|
+
${St(s.activeGates,s.gateTitles)}
|
|
12
|
+
`}var Et="roxy-data";function wt(s){return s.nodeName==="SCRIPT"&&s.getAttribute("type")==="application/json"}var F=class{constructor(e){this.host=e,e.addController(this)}hostConnected(){if(this.host.data!=null)return;let e=this.read();e!==void 0&&(this.host.data=e,this.host.requestUpdate())}read(){let e=this.findInlineScript();return e?this.parse(e.textContent):void 0}findInlineScript(){for(let e of Array.from(this.host.children))if(wt(e)&&e.classList.contains(Et))return e;return null}parse(e){if(e?.trim())try{return JSON.parse(e)}catch{return}}};function ze(s){return s?s.charAt(0).toUpperCase()+s.slice(1).toLowerCase():""}var w=class extends ${constructor(){super();this.data=null;new F(this)}render(){let t=this.data;if(!t)return m`<div class="roxy-empty" role="status">No bodygraph data</div>`;let r=new Set((t.centers??[]).filter(a=>a.defined).map(a=>a.id)),n=new Set((t.gates??[]).map(a=>a.gate).filter(a=>a!=null)),o=new Set((t.channels??[]).map(a=>je(a.gateA,a.gateB))),i=this.buildGateTitles(t.gates??[]);return m`<div class="wrap"><header class="head"><h2 class="title">Bodygraph</h2>${t.type?m`<div class="type-line">${t.type}${t.profile?m`· Profile ${t.profile}`:c}</div>`:c}</header><div class="layout"><svg viewBox="${Ge}" preserveAspectRatio="xMidYMid meet" role="img" aria-label="Human Design bodygraph with nine centers, channels, and activated gates overlaid on a human silhouette"><title>Human Design bodygraph</title><desc>Nine energy centers in their canonical positions over a human silhouette, each filled with its traditional color when defined and outlined when open, wired by channels between activated gates.</desc>${De({definedCenters:r,activeChannels:o,activeGates:n,gateTitles:i})}</svg> ${this.renderSummary(t)}</div></div>`}buildGateTitles(t){let r=new Map;for(let n of t){if(n.gate==null)continue;let o=[`Gate ${n.gate}`];n.line!=null&&(o[0]+=`.${n.line}`),n.gateName&&o.push(n.gateName);let i=n.planet?ze(n.planet):"",a=i?He[i]??i:"";a&&o.push(`${a} ${n.side??""}`.trim()),r.set(n.gate,o.join(" \xB7 "))}return r}renderSummary(t){let r=[{label:"Type",value:t.type},{label:"Strategy",value:t.strategy},{label:"Authority",value:t.authority},{label:"Profile",value:t.profile},{label:"Definition",value:t.definition}],n=t.incarnationCross;return m`<div class="summary"><div class="facts">${r.map(o=>o.value?m`<div class="fact"><span>${o.label}</span> <strong>${o.value}</strong></div>`:c)}</div>${n?.name?m`<p class="cross">${n.name} ${n.gates?.length?m`<span class="gates">(${n.gates.join(", ")})</span>`:c}</p>`:c} ${t.signature||t.notSelf?m`<div class="themes">${t.signature?m`<span class="pill pill--good">Signature: ${t.signature}</span>`:c} ${t.notSelf?m`<span class="pill pill--shadow">Not-self: ${t.notSelf}</span>`:c}</div>`:c}<div class="legend"><span class="legend-caption">Center colors when defined. Open centers are outlined.</span> <span><span class="swatch bg-gold defined"></span>Head, G</span> <span><span class="swatch bg-green defined"></span>Ajna</span> <span><span class="swatch bg-brown defined"></span>Throat, Spleen, Solar Plexus, Root</span> <span><span class="swatch bg-red defined"></span>Heart, Sacral</span> <span><span class="swatch"></span>Open center</span></div></div>`}};w.styles=[Le,T`.wrap{gap:var(--roxy-space-md,1rem);display:grid}.head{justify-content:space-between;align-items:baseline;gap:var(--roxy-space-sm,.5rem);flex-wrap:wrap;display:flex}.title{font-size:var(--roxy-text-lg,1.125rem);font-weight:var(--roxy-weight-bold,600);margin:0}.type-line{color:var(--roxy-muted,#71717a);font-size:var(--roxy-text-sm,.875rem)}.layout{gap:var(--roxy-space-lg,1.5rem);grid-template-columns:minmax(0,1fr);align-items:start;display:grid}@container (width>=520px){.layout{grid-template-columns:minmax(0,340px) minmax(0,1fr)}}svg{width:100%;max-width:340px;height:auto;margin:0 auto;display:block}.bg-body{fill:color-mix(in srgb, var(--roxy-secondary,#475569) 8%, transparent);stroke:var(--roxy-border,#e4e4e7);stroke-width:1px}.bg-channel{stroke:var(--roxy-secondary,#475569);stroke-width:1.6px;opacity:.3}.bg-channel.on{stroke-width:3.4px;stroke-linecap:round;opacity:1}.bg-half{stroke:var(--roxy-secondary,#475569);stroke-width:3.2px;stroke-linecap:round;opacity:.9}.bg-leader{stroke:var(--roxy-muted,#71717a);stroke-width:1px;opacity:.5}.bg-center{fill:#0000;stroke:var(--roxy-secondary,#475569);stroke-width:1.8px}.bg-center.defined{stroke:#00000073}.bg-center.bg-gold.defined{fill:#e0a200}.bg-center.bg-green.defined{fill:#2f8f00}.bg-center.bg-red.defined{fill:#c41f1f}.bg-center.bg-brown.defined{fill:#76502f}.bg-center-label{fill:var(--roxy-muted,#71717a);font-size:11px;font-family:var(--roxy-font-sans)}.bg-gate{fill:var(--roxy-fg,#0a0a0a);font-size:8px;font-weight:600;font-family:var(--roxy-font-sans);paint-order:stroke;stroke:var(--roxy-bg,#fff);stroke-width:1.6px;stroke-linejoin:round}.summary{gap:var(--roxy-space-md,1rem);display:grid}.facts{gap:var(--roxy-space-sm,.5rem);grid-template-columns:repeat(auto-fit,minmax(8rem,1fr));display:grid}.fact{border:1px solid var(--roxy-border,#e4e4e7);border-radius:var(--roxy-radius-md,8px);padding:var(--roxy-space-sm,.5rem) var(--roxy-space-md,1rem);background:var(--roxy-bg,#fff)}.fact span{color:var(--roxy-muted,#71717a);font-size:var(--roxy-text-xs,.75rem);text-transform:uppercase;letter-spacing:.06em;display:block}.fact strong{font-size:var(--roxy-text-base,1rem);color:var(--roxy-fg,#0a0a0a)}.cross{font-size:var(--roxy-text-sm,.875rem);color:var(--roxy-fg,#0a0a0a);border-left:2px solid var(--roxy-accent,#f59e0b);padding-left:var(--roxy-space-sm,.5rem);margin:0}.cross .gates{color:var(--roxy-muted,#71717a);font-variant-numeric:tabular-nums}.themes{gap:var(--roxy-space-sm,.5rem);flex-wrap:wrap;display:flex}.pill{border-radius:var(--roxy-radius-full,9999px);font-size:var(--roxy-text-xs,.75rem);padding:2px 10px}.pill--good{background:color-mix(in srgb, var(--roxy-success,#16a34a) 16%, transparent);color:var(--roxy-success-fg,#166534)}.pill--shadow{background:color-mix(in srgb, var(--roxy-danger,#dc2626) 16%, transparent);color:var(--roxy-danger-fg,#991b1b)}.legend{gap:var(--roxy-space-sm,.5rem) var(--roxy-space-md,1rem);font-size:var(--roxy-text-xs,.75rem);color:var(--roxy-muted,#71717a);flex-wrap:wrap;display:flex}.legend-caption{color:var(--roxy-muted,#71717a);flex-basis:100%}.legend .swatch{vertical-align:middle;border:1px solid var(--roxy-secondary,#475569);border-radius:2px;width:10px;height:10px;margin-right:4px;display:inline-block}.legend .swatch.defined{border-color:#00000073}.legend .swatch.bg-gold{background:#e0a200}.legend .swatch.bg-green{background:#2f8f00}.legend .swatch.bg-red{background:#c41f1f}.legend .swatch.bg-brown{background:#76502f}`],Z([pe({attribute:!1})],w.prototype,"data",2),w=Z([ke("roxy-bodygraph")],w);return Ke(Ct);})();
|
|
13
|
+
/*! Bundled license information:
|
|
14
|
+
|
|
15
|
+
@lit/reactive-element/css-tag.js:
|
|
16
|
+
(**
|
|
17
|
+
* @license
|
|
18
|
+
* Copyright 2019 Google LLC
|
|
19
|
+
* SPDX-License-Identifier: BSD-3-Clause
|
|
20
|
+
*)
|
|
21
|
+
|
|
22
|
+
@lit/reactive-element/reactive-element.js:
|
|
23
|
+
lit-html/lit-html.js:
|
|
24
|
+
lit-element/lit-element.js:
|
|
25
|
+
@lit/reactive-element/decorators/custom-element.js:
|
|
26
|
+
@lit/reactive-element/decorators/property.js:
|
|
27
|
+
@lit/reactive-element/decorators/state.js:
|
|
28
|
+
@lit/reactive-element/decorators/event-options.js:
|
|
29
|
+
@lit/reactive-element/decorators/base.js:
|
|
30
|
+
@lit/reactive-element/decorators/query.js:
|
|
31
|
+
@lit/reactive-element/decorators/query-all.js:
|
|
32
|
+
@lit/reactive-element/decorators/query-async.js:
|
|
33
|
+
@lit/reactive-element/decorators/query-assigned-nodes.js:
|
|
34
|
+
(**
|
|
35
|
+
* @license
|
|
36
|
+
* Copyright 2017 Google LLC
|
|
37
|
+
* SPDX-License-Identifier: BSD-3-Clause
|
|
38
|
+
*)
|
|
39
|
+
|
|
40
|
+
lit-html/is-server.js:
|
|
41
|
+
(**
|
|
42
|
+
* @license
|
|
43
|
+
* Copyright 2022 Google LLC
|
|
44
|
+
* SPDX-License-Identifier: BSD-3-Clause
|
|
45
|
+
*)
|
|
46
|
+
|
|
47
|
+
@lit/reactive-element/decorators/query-assigned-elements.js:
|
|
48
|
+
(**
|
|
49
|
+
* @license
|
|
50
|
+
* Copyright 2021 Google LLC
|
|
51
|
+
* SPDX-License-Identifier: BSD-3-Clause
|
|
52
|
+
*)
|
|
53
|
+
*/
|
|
54
|
+
//# sourceMappingURL=bodygraph.js.map
|