UNPKG

@loom-io/core

Version:

A file system wrapper for Node.js and Bun

179 lines (178 loc) 4.78 kB
export class TextItemList { before; after; _content; constructor(content) { this._content = []; this._content.push(content); } get content() { return this._content[0]; } get original() { return this._content[this._content.length - 1]; } get start() { return this.content.start; } get end() { return this.content.end; } get length() { return this.end - this.start; } isReverseRead() { return !!this.content.readReverse; } getLastForward() { if (!this.isReverseRead() && (this.after === undefined || this.after.isReverseRead())) { return this; } else if (this.isReverseRead() && (this.before === undefined || !this.before.isReverseRead())) { return this.before; } else if (this.isReverseRead()) { return this.before?.getLastForward(); } else { return this.after?.getLastForward(); } } getLastReverse() { if (this.isReverseRead() && (this.before === undefined || !this.before.isReverseRead())) { return this; } else if (!this.isReverseRead() && (this.after === undefined || this.after.isReverseRead())) { return this.after; } else if (this.isReverseRead()) { return this.before?.getLastReverse(); } else { return this.after?.getLastReverse(); } } isFirstItem() { return this.before === undefined; } getFirstItem() { let element = this; while (element.before !== undefined) { element = element.before; } return element; } isLastItem() { return this.after === undefined; } getLastItem() { let element = this; while (element.after !== undefined) { element = element.after; } return element; } add(item) { let f = item.getFirstItem(); let n; do { n = f.next(); f.separate(); if (f.start < this.start) { this.searchAndAddBefore(f); } else { this.searchAndAddAfter(f); } f = n; } while (n !== undefined); return this; } separate() { if (this.before !== undefined) { this.before.after = this.after; this.before = undefined; } if (this.after !== undefined) { this.after.before = this.before; this.after = undefined; } } searchAndAddBefore(item) { if (item.original.start === this.original.start && item.original.end === this.original.end) { return this; } let cur = this; let prev; do { prev = cur.prev(); if (prev === undefined) { return cur.addBefore(item); } else if (item.original.start > prev.original.start && item.original.start < cur.original.start) { return cur.addBefore(item); } cur = prev; } while (cur.hasPrev()); return cur.addBefore(item); } searchAndAddAfter(item) { if (item.original.start === this.original.start && item.original.end === this.original.end) { return this; } let cur = this; let next; do { next = cur.next(); if (next === undefined) { return cur.addAfter(item); } else if (item.original.start > cur.original.start && item.original.start < next.original.start) { return cur.addAfter(item); } cur = next; } while (cur.hasNext()); return cur.addAfter(item); } addBefore(item) { if (this.before !== undefined) { item.before = this.before; this.before.after = item; } item.after = this; this.before = item; return item; } addAfter(item) { item.before = this; if (this.after !== undefined) { this.after.before = item; item.after = this.after; } this.after = item; return item; } hasNext() { return this.after !== undefined; } next() { return this.after; } hasPrev() { return this.before !== undefined; } prev() { return this.before; } static patch(item, data) { item._content.unshift({ ...item.content, ...data }); } }