@miliastry/quasar 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (172) hide show
  1. package/LICENSE +119 -0
  2. package/README.md +45 -0
  3. package/dist/Visuals/lyne.css +1027 -0
  4. package/dist/Visuals/osu.css +257 -0
  5. package/dist/index.d.mts +4563 -0
  6. package/dist/index.d.ts +4563 -0
  7. package/dist/index.js +11291 -0
  8. package/dist/index.mjs +11197 -0
  9. package/package.json +51 -0
  10. package/src/Analysis/Contracts/AnalysisReport.ts +26 -0
  11. package/src/Analysis/Contracts/Contribution.ts +76 -0
  12. package/src/Analysis/Contracts/Pass.ts +76 -0
  13. package/src/Analysis/Contracts/PipelineContext.ts +48 -0
  14. package/src/Analysis/Passes/Analysis/GradientAnalyzer.ts +292 -0
  15. package/src/Analysis/Passes/Analysis/MergeableColorAnalyzer.ts +112 -0
  16. package/src/Analysis/Passes/Analysis/RainbowAnalyzer.ts +233 -0
  17. package/src/Analysis/Passes/Analysis/WaveAnalyzer.ts +211 -0
  18. package/src/Analysis/Passes/Analysis/__tests__/GradientAnalyzer.test.ts +135 -0
  19. package/src/Analysis/Passes/Analysis/__tests__/MergeableColorAnalyzer.test.ts +84 -0
  20. package/src/Analysis/Passes/Analysis/__tests__/RainbowAnalyzer.test.ts +99 -0
  21. package/src/Analysis/Passes/Analysis/__tests__/WaveAnalyzer.test.ts +119 -0
  22. package/src/Analysis/Passes/Decision/DefaultDecision.ts +139 -0
  23. package/src/Analysis/Passes/Decision/__tests__/DefaultDecision.test.ts +179 -0
  24. package/src/Analysis/Passes/Transform/CollapseGradientTransform.ts +176 -0
  25. package/src/Analysis/Passes/Transform/MergeColorsTransform.ts +126 -0
  26. package/src/Analysis/Passes/Transform/RainbowCollapseTransform.ts +83 -0
  27. package/src/Analysis/Passes/Transform/WaveCollapseTransform.ts +88 -0
  28. package/src/Analysis/Passes/Utility/CharacterCountAnalyzer.ts +45 -0
  29. package/src/Analysis/Pipeline/Pipeline.ts +133 -0
  30. package/src/Analysis/Pipeline/PipelineBuilder.ts +55 -0
  31. package/src/Analysis/Pipeline/PipelineStage.ts +19 -0
  32. package/src/Analysis/Utils/color-utils.ts +132 -0
  33. package/src/Analysis/__tests__/Integration.test.ts +162 -0
  34. package/src/Analysis/__tests__/Pipeline.test.ts +133 -0
  35. package/src/Analysis/index.ts +52 -0
  36. package/src/BBCode/BBCodeDocumentModel.ts +175 -0
  37. package/src/BBCode/BBCodeToGreenNode.ts +755 -0
  38. package/src/BBCode/Parser.ts +384 -0
  39. package/src/BBCode/index.ts +12 -0
  40. package/src/Collab/positions.ts +91 -0
  41. package/src/Commands/Command.ts +44 -0
  42. package/src/Commands/CommandRegistry.ts +78 -0
  43. package/src/Commands/DeleteNode.ts +20 -0
  44. package/src/Commands/InsertText.ts +21 -0
  45. package/src/Commands/SplitMerge.ts +28 -0
  46. package/src/Commands/WrapInTag.ts +21 -0
  47. package/src/Commands/index.ts +6 -0
  48. package/src/Diff/TreeDiffer.ts +264 -0
  49. package/src/Diff/__tests__/TreeDiffer.test.ts +65 -0
  50. package/src/Diff/index.ts +2 -0
  51. package/src/Events/EventBus.ts +160 -0
  52. package/src/Events/index.ts +2 -0
  53. package/src/Formatter/Formatter.ts +54 -0
  54. package/src/Formatter/index.ts +2 -0
  55. package/src/HTML/HTMLDocumentModel.ts +35 -0
  56. package/src/HTML/HTMLToGreenNode.ts +290 -0
  57. package/src/Incremental/ChangeTracker.ts +105 -0
  58. package/src/Incremental/IncrementalParser.ts +591 -0
  59. package/src/Incremental/__tests__/IncrementalParser.test.ts +164 -0
  60. package/src/Incremental/index.ts +4 -0
  61. package/src/Lexer/BBCodeLexer.ts +382 -0
  62. package/src/Lexer/Lexer.ts +181 -0
  63. package/src/Lexer/index.ts +10 -0
  64. package/src/Linter/Linter.ts +193 -0
  65. package/src/Linter/index.ts +2 -0
  66. package/src/Markdown/MarkdownAST.ts +112 -0
  67. package/src/Markdown/MarkdownDocumentModel.ts +55 -0
  68. package/src/Markdown/MarkdownLexer.ts +203 -0
  69. package/src/Markdown/MarkdownParser.ts +455 -0
  70. package/src/Markdown/MarkdownToGreenNode.ts +153 -0
  71. package/src/Model/DocumentModel.ts +694 -0
  72. package/src/Model/NodeFactory.ts +117 -0
  73. package/src/Model/TagRegistry.ts +495 -0
  74. package/src/Model/index.ts +5 -0
  75. package/src/Plugins/PluginAPI.ts +119 -0
  76. package/src/Plugins/PluginRegistry.ts +132 -0
  77. package/src/Plugins/index.ts +3 -0
  78. package/src/Queries/QueryEngine.ts +152 -0
  79. package/src/Queries/index.ts +1 -0
  80. package/src/RenderPipeline/RenderPipeline.ts +125 -0
  81. package/src/RenderPipeline/RenderTree.ts +134 -0
  82. package/src/RenderPipeline/index.ts +4 -0
  83. package/src/Semantic/SemanticAnalyzer.ts +506 -0
  84. package/src/Semantic/index.ts +2 -0
  85. package/src/Symbols/SymbolTable.ts +124 -0
  86. package/src/Symbols/index.ts +1 -0
  87. package/src/Syntax/GreenNode.ts +324 -0
  88. package/src/Syntax/GreenNodePool.ts +269 -0
  89. package/src/Syntax/NodeMatcher.ts +370 -0
  90. package/src/Syntax/RedNode.ts +569 -0
  91. package/src/Syntax/RedNodeStore.ts +184 -0
  92. package/src/Syntax/TreeBuilder.ts +214 -0
  93. package/src/Syntax/__tests__/GreenNode.test.ts +33 -0
  94. package/src/Syntax/__tests__/RedNode.test.ts +81 -0
  95. package/src/Syntax/__tests__/RedNodeStore.test.ts +104 -0
  96. package/src/Syntax/greenEdit.ts +110 -0
  97. package/src/Syntax/hash.ts +30 -0
  98. package/src/Syntax/index.ts +12 -0
  99. package/src/Syntax/partition.ts +161 -0
  100. package/src/Syntax/preserveNodeIds.ts +201 -0
  101. package/src/Tests/ASTOptimizerIdempotence.test.ts +77 -0
  102. package/src/Tests/BlockPatcher.test.ts +437 -0
  103. package/src/Tests/BlockPatcherWindowed.test.ts +364 -0
  104. package/src/Tests/BoxDrawer.test.ts +217 -0
  105. package/src/Tests/BoxRichTitle.test.ts +105 -0
  106. package/src/Tests/Chars500kBenchmark.test.ts +151 -0
  107. package/src/Tests/Chars500kEdits.test.ts +321 -0
  108. package/src/Tests/CollabPositions.test.ts +146 -0
  109. package/src/Tests/CompilerPathProfiling.test.ts +186 -0
  110. package/src/Tests/DOMMorpher.test.ts +142 -0
  111. package/src/Tests/DomPatchPerf.test.ts +60 -0
  112. package/src/Tests/EffectSegments.snapshot.json +616 -0
  113. package/src/Tests/EffectSegments.test.ts +68 -0
  114. package/src/Tests/FindNodeAtOffset.test.ts +65 -0
  115. package/src/Tests/Fuzzer.test.ts +166 -0
  116. package/src/Tests/GreenNodePool.test.ts +153 -0
  117. package/src/Tests/Lexer.test.ts +238 -0
  118. package/src/Tests/LyneMode.test.ts +187 -0
  119. package/src/Tests/ModelCoherence.test.ts +180 -0
  120. package/src/Tests/Partition.test.ts +238 -0
  121. package/src/Tests/PluginTags.test.ts +150 -0
  122. package/src/Tests/ProblematicSection.test.ts +46 -0
  123. package/src/Tests/ProblematicSectionHTML.test.ts +58 -0
  124. package/src/Tests/RedReuse.test.ts +134 -0
  125. package/src/Tests/ReproDelete20k.test.ts +62 -0
  126. package/src/Tests/SemanticValidators.test.ts +136 -0
  127. package/src/Tests/StableNodeIds.test.ts +210 -0
  128. package/src/Tests/StudioColorBloat.test.ts +25 -0
  129. package/src/Tests/StudioDebugText.test.ts +27 -0
  130. package/src/Tests/StudioTrailingChar.test.ts +25 -0
  131. package/src/Tests/StudioValidText.test.ts +25 -0
  132. package/src/Tests/UrlImgBug.test.ts +23 -0
  133. package/src/Tests/VisualBuilderFidelity.test.ts +105 -0
  134. package/src/Tests/referenceDocument.ts +119 -0
  135. package/src/Transactions/Transaction.ts +176 -0
  136. package/src/Transactions/UndoManager.ts +111 -0
  137. package/src/Transactions/index.ts +3 -0
  138. package/src/Transformers/ASTOptimizer.ts +315 -0
  139. package/src/Transformers/GradientTransformer.ts +143 -0
  140. package/src/Transformers/GrowTransformer.ts +115 -0
  141. package/src/Transformers/RainbowTransformer.ts +121 -0
  142. package/src/Transformers/SineWaveTransformer.ts +130 -0
  143. package/src/Transformers/Transformer.ts +22 -0
  144. package/src/Types/core.ts +270 -0
  145. package/src/Types/diagnostics.ts +156 -0
  146. package/src/Types/index.ts +23 -0
  147. package/src/Types/operations.ts +180 -0
  148. package/src/Types/queries.ts +121 -0
  149. package/src/Types/symbols.ts +69 -0
  150. package/src/Types/tokens.ts +186 -0
  151. package/src/Utils/BBCodeGenerator.ts +126 -0
  152. package/src/Utils/ColorMath.ts +276 -0
  153. package/src/Utils/color.ts +112 -0
  154. package/src/Utils/dom-to-svg.test.ts +86 -0
  155. package/src/Utils/dom-to-svg.ts +615 -0
  156. package/src/Utils/treeTransformers.ts +717 -0
  157. package/src/Visitors/BBBlocksExporter.ts +69 -0
  158. package/src/Visitors/BBCodeExporter.ts +318 -0
  159. package/src/Visitors/BlockPatcher.ts +963 -0
  160. package/src/Visitors/DOMMorpher.ts +134 -0
  161. package/src/Visitors/HTMLRenderer.ts +1077 -0
  162. package/src/Visitors/JSONExporter.ts +66 -0
  163. package/src/Visitors/MarkdownExporter.ts +99 -0
  164. package/src/Visitors/SVGRenderer.ts +35 -0
  165. package/src/Visitors/TiptapExporter.ts +145 -0
  166. package/src/Visitors/Visitor.ts +48 -0
  167. package/src/Visitors/index.ts +9 -0
  168. package/src/Visuals/BoxDrawer.ts +175 -0
  169. package/src/Visuals/index.ts +42 -0
  170. package/src/Visuals/lyne.css +1027 -0
  171. package/src/Visuals/osu.css +257 -0
  172. package/src/index.ts +197 -0
@@ -0,0 +1,134 @@
1
+ /**
2
+ * DocumentEngine — DOMMorpher
3
+ *
4
+ * Reconciles and morphs an existing HTML DOM tree in-place to match a new HTML string.
5
+ * Operating on pure HTML string output from HTMLRenderer means ZERO changes to Quasar AST schemas.
6
+ *
7
+ * Features:
8
+ * - In-place attribute synchronization
9
+ * - In-place text node value updates
10
+ * - Preserves state of unchanged elements (spoilers, audio/video, selections)
11
+ * - Zero extra wrapper <div> elements
12
+ */
13
+
14
+ export function morphHTML(container: HTMLElement, newHTML: string): void {
15
+ if (container.childNodes.length === 0) {
16
+ container.innerHTML = newHTML
17
+ return
18
+ }
19
+
20
+ const template = document.createElement('template')
21
+ template.innerHTML = newHTML
22
+
23
+ morphNodes(container, template.content)
24
+ }
25
+
26
+ /**
27
+ * Reconcile `parent`'s children against `newParent`'s.
28
+ *
29
+ * Children are paired positionally, which is why the identical prefix and
30
+ * suffix are trimmed first: without that, inserting a single node near the
31
+ * start shifts every following sibling by one, so each one compares against the
32
+ * wrong counterpart and gets rewritten — the exact cascade a morpher exists to
33
+ * avoid.
34
+ *
35
+ * Trimming uses `isEqualNode`, a native deep structural comparison. A subtree
36
+ * that compares equal is left completely untouched: no recursion, no attribute
37
+ * loops, and — because the DOM node is never replaced — any runtime state it
38
+ * holds (open spoilers, media playback, selection) survives for free.
39
+ *
40
+ * Note on keys: the obvious next step would be pairing by `data-node-id`, but
41
+ * those are regenerated on every parse. Measured on a one-character edit,
42
+ * **zero** ids survive a rebuild, so keying on them would make every node look
43
+ * new and reduce the morpher to a full replacement. That needs identity that is
44
+ * stable across re-parses first.
45
+ */
46
+ function morphNodes(parent: Node, newParent: Node): void {
47
+ const oldNodes = parent.childNodes
48
+ const newNodes = newParent.childNodes
49
+
50
+ // ── Phase 1: trim the identical prefix and suffix ──────────────
51
+ // Nothing is mutated here, so reading the live NodeLists is safe.
52
+ const limit = Math.min(oldNodes.length, newNodes.length)
53
+
54
+ let lo = 0
55
+ while (lo < limit && oldNodes[lo].isEqualNode(newNodes[lo])) lo++
56
+
57
+ let oldHi = oldNodes.length - 1
58
+ let newHi = newNodes.length - 1
59
+ while (oldHi >= lo && newHi >= lo && oldNodes[oldHi].isEqualNode(newNodes[newHi])) {
60
+ oldHi--
61
+ newHi--
62
+ }
63
+
64
+ // Everything matched — this whole level is already correct.
65
+ if (lo > oldHi && lo > newHi) return
66
+
67
+ // ── Phase 2: reconcile only the window between them ────────────
68
+ // Snapshot before touching anything: the loop mutates `parent`, which would
69
+ // shift a live NodeList underneath us. Only the changed window is copied.
70
+ const oldChildren: Node[] = []
71
+ for (let i = lo; i <= oldHi; i++) oldChildren.push(oldNodes[i])
72
+ const newChildren: Node[] = []
73
+ for (let i = lo; i <= newHi; i++) newChildren.push(newNodes[i])
74
+
75
+ // Insertions must land before the preserved suffix, not at the end. Captured
76
+ // now, while indices still refer to the pre-mutation DOM.
77
+ const suffixAnchor: Node | null = oldNodes[oldHi + 1] ?? null
78
+
79
+ const maxLen = Math.max(oldChildren.length, newChildren.length)
80
+
81
+ for (let i = 0; i < maxLen; i++) {
82
+ const oldNode = oldChildren[i]
83
+ const newNode = newChildren[i]
84
+
85
+ if (!oldNode && newNode) {
86
+ parent.insertBefore(newNode.cloneNode(true), suffixAnchor)
87
+ } else if (oldNode && !newNode) {
88
+ parent.removeChild(oldNode)
89
+ } else if (oldNode && newNode) {
90
+ if (oldNode.nodeType === 3 && newNode.nodeType === 3) {
91
+ // Text node: update nodeValue in-place
92
+ if (oldNode.nodeValue !== newNode.nodeValue) {
93
+ oldNode.nodeValue = newNode.nodeValue
94
+ }
95
+ } else if (
96
+ oldNode.nodeType === 1 &&
97
+ newNode.nodeType === 1 &&
98
+ (oldNode as Element).tagName === (newNode as Element).tagName
99
+ ) {
100
+ const oldEl = oldNode as Element
101
+ const newEl = newNode as Element
102
+
103
+ // Preserve interactive runtime states (such as <details open> for spoilerboxes and boxes)
104
+ if (oldEl.tagName === 'DETAILS' && oldEl.hasAttribute('open')) {
105
+ newEl.setAttribute('open', '')
106
+ }
107
+ if (oldEl.classList.contains('open')) {
108
+ newEl.classList.add('open')
109
+ }
110
+ if (oldEl.classList.contains('is-open')) {
111
+ newEl.classList.add('is-open')
112
+ }
113
+
114
+ // Sync attributes in-place
115
+ for (const attr of Array.from(newEl.attributes)) {
116
+ if (oldEl.getAttribute(attr.name) !== attr.value) {
117
+ oldEl.setAttribute(attr.name, attr.value)
118
+ }
119
+ }
120
+ for (const attr of Array.from(oldEl.attributes)) {
121
+ if (!newEl.hasAttribute(attr.name)) {
122
+ oldEl.removeAttribute(attr.name)
123
+ }
124
+ }
125
+
126
+ // Morph child nodes recursively
127
+ morphNodes(oldEl, newEl)
128
+ } else {
129
+ // Different tag or nodeType: replace node
130
+ oldNode.parentNode!.replaceChild(newNode.cloneNode(true), oldNode)
131
+ }
132
+ }
133
+ }
134
+ }