import { escapeHtml } from "../inline/render.js"; import type { BlockHandler, IdentifyResult } from "./handler.type.js"; /** * Match a standalone image line: `![alt](url)` or `![alt](url "title")`. * The entire trimmed line must be the image — no surrounding text. */ const IMAGE_RE = /^!\[([^\]]*)\]\((\S+?)(?:\s+"([^"]*)")?\)$/; export const imageHandler = { identify(lines: string[], index: number): IdentifyResult | null { const trimmed = lines[index].trim(); const match = trimmed.match(IMAGE_RE); if (!match) return null; const [, alt, src, title] = match; const attrs: Record = { src }; if (title !== undefined) attrs.title = title; return { raw: alt, attrs, nextIndex: index + 1 }; }, render(raw: string, attrs?: Record): string { const src = escapeHtml(attrs?.src ?? ""); const alt = escapeHtml(raw); const title = attrs?.title; let img = `${alt}${img}`; }, serialize(raw: string, attrs?: Record): string { const src = attrs?.src ?? ""; const title = attrs?.title; if (title !== undefined) { return `![${raw}](${src} "${title}")`; } return `![${raw}](${src})`; }, } satisfies BlockHandler;