/** * Normalizes an origin document's text for *encoding*, never for content. * * Does: folds every line-break form to LF; strips the byte-order mark, * control characters other than LF and tab, bidirectional controls, * zero-width characters, tag characters, and stray variation selectors — * while preserving emoji ZWJ, keycap, CJK, Mongolian, and emoji-tag * sequences; composes to Unicode NFC; trims leading and trailing whitespace. * * Does not: collapse internal whitespace, reflow paragraphs, fold smart * quotes or dashes, case-fold, or strip punctuation, diacritics, emoji, or * non-ASCII characters. The document is meant to be the original. * * Idempotent — `normalizeOriginText(normalizeOriginText(t))` equals * `normalizeOriginText(t)` — which is what makes it safe to apply both at an * application's import boundary and again on document creation. * * Two things make it idempotent, and both are load-bearing. * * The step order. Line breaks are folded first because a lone carriage return * is itself a control character, so stripping first would delete the break * rather than convert it. Stripping precedes NFC because removing an invisible * character can leave a base letter adjacent to a combining mark it was * previously separated from; composing first would leave that pair for a second * application to compose. NFC never emits a control, an invisible, or a line * break, so the reverse hazard does not exist. * * And the rule that a removal candidate never legitimizes another removal * candidate — see `isLegitimateInContext`. Without it a character survives on * the strength of a neighbour deleted in the same pass, and the next pass * deletes it too. */ export declare function normalizeOriginText(text: string): string; /** The number of Unicode code points in a string — not its UTF-16 `length`. */ export declare function codePointLength(text: string): number; /** * A reusable code-point↔UTF-16 offset map for one document. * * Build it once per document and reuse it across that document's anchors; * resolving N anchors with `sliceByCodePoints` instead costs a full scan per * anchor. */ export type TCodePointIndex = { readonly text: string; /** UTF-16 offset of each code point, with one extra entry for the end of the string. */ readonly offsets: readonly number[]; }; /** Builds the reusable offset map described by {@link TCodePointIndex}. */ export declare function buildCodePointIndex(text: string): TCodePointIndex; /** * Slices a string by **code-point** offsets. * * `String.prototype.slice` on the same offsets is wrong for any text * containing an astral-plane character, and passes every ASCII test — which * is why anchor fields are named `startCodePoint` / `endCodePoint` and why * this helper exists. Offsets are clamped rather than rejected; range * checking against a document belongs to the origin library's validation. */ export declare function sliceByCodePoints(text: string, startCodePoint: number, endCodePoint: number): string; /** {@link sliceByCodePoints} against a prebuilt {@link TCodePointIndex}. */ export declare function sliceByCodePointsIndexed(index: TCodePointIndex, startCodePoint: number, endCodePoint: number): string; //# sourceMappingURL=origin-text.d.ts.map