/** * Kombination: konsolidierte Darstellung globales Profil + Stationen mit Zeiten (Vorschau, Plan-Ansicht, Druck). */ import React, { useMemo } from 'react' import { archetypeCoachHint, combinationArchetypeLabel, sortCombinationSlotsForDisplay, } from '../constants/combinationArchetypes' import { describeGlobalComboProfile, effectiveStationTimingSummary, readSlotProfilesV1 } from '../utils/combinationMethodProfileUi' function candidateLine(slot) { const cands = slot.candidates if (Array.isArray(cands) && cands.length > 0) { return cands .map((c) => ((c.title || '').trim() || (c.exercise_id != null ? `Übung #${c.exercise_id}` : '')).trim(), ) .filter(Boolean) .join(' ↔ ') } const ids = slot.candidate_exercise_ids || [] return ids .map((raw) => { const n = typeof raw === 'number' ? raw : parseInt(String(raw), 10) return Number.isFinite(n) ? `Übung #${n}` : '' }) .filter(Boolean) .join(' ↔ ') } export default function CombinationPlanBracket({ methodArchetype, methodProfile, combinationSlots, planningAdjusted = false, }) { const arch = typeof methodArchetype === 'string' ? methodArchetype.trim() : '' const archLabel = arch ? combinationArchetypeLabel(arch) : null const globals = describeGlobalComboProfile(arch, methodProfile || {}) const slotsSorted = useMemo(() => sortCombinationSlotsForDisplay(combinationSlots || []), [combinationSlots]) const timingByIx = useMemo(() => { const mp = methodProfile || {} const rows = readSlotProfilesV1(mp) const m = new Map() for (const r of rows) { m.set(Number(r.slot_index), r) } return m }, [methodProfile]) const coachHint = arch ? archetypeCoachHint(arch) : '' return (
Kombinations‑Plan {archLabel || arch || 'Archetyp'} {arch && archLabel && archLabel !== arch ? ( ({arch}) ) : null} {planningAdjusted ? ( Planung angepasst ) : null}
{coachHint ?

{coachHint}

: null}
{globals.length > 0 ? (
Runden · Zeiten · Pausen (global)
    {globals.map((g) => (
  • {g.caption} {g.value}
  • ))}
) : (

Keine globalen Zahlenfelder gesetzt — Steuerung erfolgt nur je Station oder über den Freitext der Kombination.

)}
    {slotsSorted.map((slot, si) => { const siRaw = slot.slot_index const ixParsed = siRaw === '' || siRaw == null ? si : typeof siRaw === 'number' ? siRaw : parseInt(String(siRaw), 10) const stationIx = Number.isFinite(ixParsed) ? ixParsed : si const displayStep = si + 1 const stationTitle = ((slot.title || '').trim() || `Station ${displayStep}`).trim() const names = candidateLine(slot) const timing = effectiveStationTimingSummary(arch, methodProfile || {}, timingByIx.get(stationIx)) return (
  1. S{displayStep}
    {stationTitle}
    {names || '(keine Einzelübung)'}
    {timing ? (
    Zeit / Steuerung {timing}
    ) : (
    Keine eigene Stations‑Zeit im Profil — ggf. nur globale Vorgaben oder Freitext.
    )}
  2. ) })}
) }