import { Facet, RangeSetBuilder } from "@codemirror/state";
import {
  Decoration,
  EditorView,
  ViewPlugin,
  WidgetType
} from "@codemirror/view";
import { scanScopeRefs } from "./scope-refs.js";
export const scopeLookupFacet = Facet.define({
  combine: (values) => values.length > 0 ? values[values.length - 1] : /* @__PURE__ */ new Map()
});
class ScopeChipWidget extends WidgetType {
  constructor(id, member, resolved) {
    super();
    this.id = id;
    this.member = member;
    this.resolved = resolved;
  }
  eq(other) {
    return other.id === this.id && other.member === this.member && other.resolved?.origin === this.resolved?.origin && other.resolved?.label === this.resolved?.label && other.resolved?.type === this.resolved?.type;
  }
  toDOM() {
    const chip = document.createElement("span");
    chip.className = "cm-scope-chip";
    chip.setAttribute("data-scope-id", this.id);
    chip.setAttribute("data-scope-member", this.member);
    const text = document.createElement("span");
    text.className = "cm-scope-chip-label";
    if (this.resolved) {
      text.textContent = `${this.resolved.origin} \u203A ${this.resolved.label}`;
      chip.title = this.resolved.origin;
    } else {
      chip.classList.add("cm-scope-chip-dangling");
      const short = this.id.length > 8 ? `${this.id.slice(0, 8)}\u2026` : this.id;
      text.textContent = `${short} \u203A ${this.member}`;
      chip.title = `\u672A\u77E5\u4F5C\u7528\u57DF ${this.id}`;
    }
    chip.appendChild(text);
    const type = this.resolved?.type;
    if (type) {
      const badge = document.createElement("span");
      badge.className = "cm-scope-chip-type";
      badge.textContent = type;
      chip.appendChild(badge);
    }
    return chip;
  }
  ignoreEvent() {
    return false;
  }
}
function buildChips(view) {
  const lookup = view.state.facet(scopeLookupFacet);
  const builder = new RangeSetBuilder();
  for (const ref of scanScopeRefs(view.state.doc.toString())) {
    const info = lookup.get(ref.id);
    const member = info?.members.get(ref.member);
    const resolved = info && member ? { origin: info.origin, label: member.label, type: member.type } : null;
    builder.add(
      ref.from,
      ref.to,
      Decoration.replace({ widget: new ScopeChipWidget(ref.id, ref.member, resolved) })
    );
  }
  return builder.finish();
}
const chipPlugin = ViewPlugin.fromClass(
  class {
    decorations;
    constructor(view) {
      this.decorations = buildChips(view);
    }
    update(update) {
      if (update.docChanged || update.viewportChanged || update.startState.facet(scopeLookupFacet) !== update.state.facet(scopeLookupFacet)) {
        this.decorations = buildChips(update.view);
      }
    }
  },
  {
    decorations: (plugin) => plugin.decorations,
    // Atomic ranges so the caret steps over a chip and Backspace removes the
    // whole `__scopes__[...].member` at once — the user's delete-as-unit choice.
    provide: (plugin) => EditorView.atomicRanges.of((view) => view.plugin(plugin)?.decorations ?? Decoration.none)
  }
);
const chipTheme = EditorView.theme({
  ".cm-scope-chip": {
    display: "inline-flex",
    alignItems: "center",
    gap: "0.25rem",
    margin: "0 1px",
    padding: "0.125rem 0.25rem",
    borderRadius: "0.25rem",
    background: "#f4f4f5",
    border: "1px solid #e4e4e7",
    color: "#3f3f46",
    fontFamily: "ui-sans-serif, system-ui, sans-serif",
    verticalAlign: "baseline",
    cursor: "default",
    whiteSpace: "nowrap"
  },
  ".cm-scope-chip-dangling": {
    background: "#fef2f2",
    borderColor: "#fecaca",
    color: "#b91c1c"
  },
  ".cm-scope-chip-label": {
    fontSize: "0.75rem",
    lineHeight: "1.1"
  },
  ".cm-scope-chip-type": {
    borderRadius: "0.25rem",
    background: "#f3e8ff",
    padding: "0.05rem 0.25rem",
    fontFamily: "var(--font-mono)",
    fontSize: "10px",
    lineHeight: "1",
    color: "#7e22ce"
  }
});
export function scopeChips() {
  return [chipPlugin, chipTheme];
}
