fix(chart): keep zero-year chara and ephemeris dates apart
A zero-year Chara period is shown as 0 years instead of failing the whole chart. Switching ephemeris dates drops the previous day immediately and can be retried. Missing birth data links to chart settings.
This commit is contained in:
@@ -82,11 +82,19 @@ function isoDay(value: string): string {
|
||||
function addWeightedSpan(startIso: string, endIso: string, index: number, weights: readonly number[]): { start: string; end: string } {
|
||||
const start = Date.parse(`${startIso}T00:00:00Z`);
|
||||
const end = Date.parse(`${endIso}T00:00:00Z`);
|
||||
const total = weights.reduce((sum, weight) => sum + weight, 0);
|
||||
const before = weights.slice(0, index).reduce((sum, weight) => sum + weight, 0);
|
||||
const total = weights.reduce((sum, weight) => sum + (Number.isFinite(weight) ? weight : 0), 0);
|
||||
// A zero-year Chara mahadasha gives every antardasha weight 0. `??` does not
|
||||
// replace 0, so total is 0 and `before / total` is NaN. Never call
|
||||
// `Date#toISOString` on that — it throws RangeError and fails the whole chart.
|
||||
if (!Number.isFinite(start) || !Number.isFinite(end) || !(total > 0)) {
|
||||
return { start: startIso, end: startIso };
|
||||
}
|
||||
const before = weights.slice(0, index).reduce((sum, weight) => sum + (Number.isFinite(weight) ? weight : 0), 0);
|
||||
const weight = Number.isFinite(weights[index]) ? weights[index]! : 0;
|
||||
const span = end - start;
|
||||
const from = start + span * (before / total);
|
||||
const to = index === weights.length - 1 ? end : start + span * ((before + weights[index]!) / total);
|
||||
const to = index === weights.length - 1 ? end : start + span * ((before + weight) / total);
|
||||
if (!Number.isFinite(from) || !Number.isFinite(to)) return { start: startIso, end: startIso };
|
||||
return { start: new Date(from).toISOString().slice(0, 10), end: new Date(to).toISOString().slice(0, 10) };
|
||||
}
|
||||
|
||||
@@ -390,12 +398,16 @@ function charaTrack(charaPacket: Record<string, unknown> | null, birthDate: stri
|
||||
if (!row) return [];
|
||||
const sign = text(row.sign);
|
||||
const lord = text(row.lord) ?? sign ?? "—";
|
||||
const duration = finite(row.duration_years) ?? 1;
|
||||
const rawDuration = finite(row.duration_years);
|
||||
const duration = rawDuration === null ? 1 : rawDuration;
|
||||
const zeroYear = duration === 0;
|
||||
const start = cursor;
|
||||
const end = addYears(start, duration);
|
||||
cursor = end;
|
||||
const rawAntar = Array.isArray(row.antardashas) ? row.antardashas : [];
|
||||
const antardashas = rawAntar.length > 0
|
||||
const antardashas = zeroYear
|
||||
? []
|
||||
: rawAntar.length > 0
|
||||
? rawAntar.flatMap((antar, index) => {
|
||||
const item = record(antar);
|
||||
if (!item) return [];
|
||||
@@ -430,6 +442,7 @@ function charaTrack(charaPacket: Record<string, unknown> | null, birthDate: stri
|
||||
end,
|
||||
current: containsDay(start, end, asOf),
|
||||
derived: false,
|
||||
...(zeroYear ? { zeroYear: true as const } : {}),
|
||||
antardashas,
|
||||
}];
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user