<script lang="ts">
  import { derived, toStore } from "svelte/store";

  import Stack from "../stack/Stack.svelte";
  import { useConditionContext } from "../../stores/condition-context.svelte";
  import {
    getRequiredLoaderContext,
    setLoaderContext,
    type LoaderContextValue,
  } from "../../stores/loader";
  import type { LoaderGroupItemProps } from "../../types/components/loader-group";
  import { resolveOverrideProperties } from "../../utils/style-utils";

  const props: LoaderGroupItemProps = $props();

  const buildConditionContext = useConditionContext({ state: true });
  const actualProps = $derived({
    ...props,
    ...resolveOverrideProperties(buildConditionContext(), props.overrides),
  });

  const isVisible = $derived(actualProps.visible !== false);

  const ambientLoader = getRequiredLoaderContext(props.type);

  // toStore: a plain store `derived` only re-runs on ambientLoader emits, not
  // on rune reads — starts_at/ends_at overrides would freeze once the loader
  // hits 100% and unsubscribes.
  const localLoader = derived(
    [ambientLoader, toStore(() => actualProps)],
    ([$ambientLoader, $actualProps]): LoaderContextValue => {
      const span = $actualProps.ends_at - $actualProps.starts_at;
      // Fallback for malformed payload (e.g. ends_at <= starts_at)
      if (span <= 0) return { progress: 0 };
      const pct =
        ($ambientLoader.progress * 100 - $actualProps.starts_at) / span;
      return { progress: Math.min(1, Math.max(0, pct)) };
    },
  );

  setLoaderContext(localLoader);
</script>

{#if isVisible}
  <Stack {...actualProps.stack} testId="loader-group-item" />
{/if}
