import { createContext, useContext } from "solid-js";

/**
 * Registry for description/error message ids rendered inside a `<Field.Root>`.
 *
 * `<Field.Description>` and `<Field.Error>` each generate a unique id, register
 * it here on setup, and unregister on cleanup. `<Field.Control>` reads
 * `getMessageIds()` and composes them into `aria-describedby` so assistive tech
 * announces the related help text / error messages.
 *
 * Keyed by a per-consumer `symbol` so multiple simultaneous messages (e.g. a
 * description AND an error) can coexist without stepping on each other.
 *
 * Registration order is preserved: `getMessageIds()` returns ids in the order
 * they were registered, which matches render order for typical
 * "description before error" layouts.
 *
 * ### Why a dedicated registry?
 *
 * The shared `<LabelableProvider>` already exposes a `registerLabelId` / label
 * registry (used by `<Field.Label>`), plus a `controlId` slot. React's version
 * had a third slot — `messageIds` — that Description/Error wrote into. The
 * Solid port's `LabelableProvider` hasn't followed that design: keeping the
 * message-id channel here keeps the labelable provider focused on the
 * labelled/controlId pair, and avoids touching shared internals.
 */

const NOOP = () => {};
const EMPTY_IDS = Object.freeze([]);

/**
 * Returned when no `<Field.Root>` is above a `<Field.Description>` /
 * `<Field.Error>` — the registry is a no-op and the registered ids list is
 * empty.
 */
export const NOOP_FIELD_MESSAGES_CONTEXT = {
  registerMessageId: NOOP,
  getMessageIds: () => EMPTY_IDS,
  present: false
};
export const FieldMessagesContext = createContext(NOOP_FIELD_MESSAGES_CONTEXT);

/**
 * Read the nearest `<Field.Root>` message-id registry. Returns the noop
 * context when no `<Field.Root>` is above — callers can branch on `.present`.
 */
export function useFieldMessagesContext() {
  return useContext(FieldMessagesContext);
}
//# sourceMappingURL=field-messages-context.jsx.map
