react-native-richify 1.0.1 → 1.0.3
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.
- package/lib/commonjs/components/OverlayText.d.js +6 -0
- package/lib/commonjs/components/OverlayText.d.js.map +1 -0
- package/lib/commonjs/components/OverlayText.js +51 -0
- package/lib/commonjs/components/OverlayText.js.map +1 -0
- package/lib/commonjs/components/RichTextInput.d.js +6 -0
- package/lib/commonjs/components/RichTextInput.d.js.map +1 -0
- package/lib/commonjs/components/RichTextInput.js +163 -0
- package/lib/commonjs/components/RichTextInput.js.map +1 -0
- package/lib/commonjs/components/Toolbar.d.js +6 -0
- package/lib/commonjs/components/Toolbar.d.js.map +1 -0
- package/lib/commonjs/components/Toolbar.js +96 -0
- package/lib/commonjs/components/Toolbar.js.map +1 -0
- package/lib/commonjs/components/ToolbarButton.d.js +6 -0
- package/lib/commonjs/components/ToolbarButton.d.js.map +1 -0
- package/lib/commonjs/components/ToolbarButton.js +63 -0
- package/lib/commonjs/components/ToolbarButton.js.map +1 -0
- package/lib/commonjs/constants/defaultStyles.d.js +6 -0
- package/lib/commonjs/constants/defaultStyles.d.js.map +1 -0
- package/lib/commonjs/constants/defaultStyles.js +172 -0
- package/lib/commonjs/constants/defaultStyles.js.map +1 -0
- package/lib/commonjs/context/RichTextContext.d.js +6 -0
- package/lib/commonjs/context/RichTextContext.d.js.map +1 -0
- package/lib/commonjs/context/RichTextContext.js +61 -0
- package/lib/commonjs/context/RichTextContext.js.map +1 -0
- package/lib/commonjs/hooks/useFormatting.d.js +6 -0
- package/lib/commonjs/hooks/useFormatting.d.js.map +1 -0
- package/lib/commonjs/hooks/useFormatting.js +82 -0
- package/lib/commonjs/hooks/useFormatting.js.map +1 -0
- package/lib/commonjs/hooks/useRichText.d.js +6 -0
- package/lib/commonjs/hooks/useRichText.d.js.map +1 -0
- package/lib/commonjs/hooks/useRichText.js +142 -0
- package/lib/commonjs/hooks/useRichText.js.map +1 -0
- package/lib/commonjs/hooks/useSelection.d.js +6 -0
- package/lib/commonjs/hooks/useSelection.d.js.map +1 -0
- package/lib/commonjs/hooks/useSelection.js +39 -0
- package/lib/commonjs/hooks/useSelection.js.map +1 -0
- package/lib/commonjs/index.d.js +186 -0
- package/lib/commonjs/index.d.js.map +1 -0
- package/lib/commonjs/index.js +186 -0
- package/lib/commonjs/index.js.map +1 -0
- package/lib/commonjs/package.json +1 -0
- package/lib/commonjs/types/index.d.js +6 -0
- package/lib/commonjs/types/index.d.js.map +1 -0
- package/lib/commonjs/types/index.js +6 -0
- package/lib/commonjs/types/index.js.map +1 -0
- package/lib/commonjs/utils/formatter.d.js +13 -0
- package/lib/commonjs/utils/formatter.d.js.map +1 -0
- package/lib/commonjs/utils/formatter.js +229 -0
- package/lib/commonjs/utils/formatter.js.map +1 -0
- package/lib/commonjs/utils/parser.d.js +6 -0
- package/lib/commonjs/utils/parser.d.js.map +1 -0
- package/lib/commonjs/utils/parser.js +221 -0
- package/lib/commonjs/utils/parser.js.map +1 -0
- package/lib/commonjs/utils/styleMapper.d.js +6 -0
- package/lib/commonjs/utils/styleMapper.d.js.map +1 -0
- package/lib/commonjs/utils/styleMapper.js +87 -0
- package/lib/commonjs/utils/styleMapper.js.map +1 -0
- package/lib/module/components/OverlayText.d.js +4 -0
- package/lib/module/components/OverlayText.d.js.map +1 -0
- package/lib/module/components/OverlayText.js +47 -0
- package/lib/module/components/OverlayText.js.map +1 -0
- package/lib/module/components/RichTextInput.d.js +4 -0
- package/lib/module/components/RichTextInput.d.js.map +1 -0
- package/lib/module/components/RichTextInput.js +158 -0
- package/lib/module/components/RichTextInput.js.map +1 -0
- package/lib/module/components/Toolbar.d.js +4 -0
- package/lib/module/components/Toolbar.d.js.map +1 -0
- package/lib/module/components/Toolbar.js +92 -0
- package/lib/module/components/Toolbar.js.map +1 -0
- package/lib/module/components/ToolbarButton.d.js +4 -0
- package/lib/module/components/ToolbarButton.d.js.map +1 -0
- package/lib/module/components/ToolbarButton.js +59 -0
- package/lib/module/components/ToolbarButton.js.map +1 -0
- package/lib/module/constants/defaultStyles.d.js +4 -0
- package/lib/module/constants/defaultStyles.d.js.map +1 -0
- package/lib/module/constants/defaultStyles.js +168 -0
- package/lib/module/constants/defaultStyles.js.map +1 -0
- package/lib/module/context/RichTextContext.d.js +4 -0
- package/lib/module/context/RichTextContext.d.js.map +1 -0
- package/lib/module/context/RichTextContext.js +55 -0
- package/lib/module/context/RichTextContext.js.map +1 -0
- package/lib/module/hooks/useFormatting.d.js +11 -0
- package/lib/module/hooks/useFormatting.d.js.map +1 -0
- package/lib/module/hooks/useFormatting.js +78 -0
- package/lib/module/hooks/useFormatting.js.map +1 -0
- package/lib/module/hooks/useRichText.d.js +4 -0
- package/lib/module/hooks/useRichText.d.js.map +1 -0
- package/lib/module/hooks/useRichText.js +138 -0
- package/lib/module/hooks/useRichText.js.map +1 -0
- package/lib/module/hooks/useSelection.d.js +4 -0
- package/lib/module/hooks/useSelection.d.js.map +1 -0
- package/lib/module/hooks/useSelection.js +35 -0
- package/lib/module/hooks/useSelection.js.map +1 -0
- package/lib/module/index.d.js +15 -0
- package/lib/module/index.d.js.map +1 -0
- package/lib/module/index.js +25 -0
- package/lib/module/index.js.map +1 -0
- package/lib/module/types/index.d.js +4 -0
- package/lib/module/types/index.d.js.map +1 -0
- package/lib/module/types/index.js +4 -0
- package/lib/module/types/index.js.map +1 -0
- package/lib/module/utils/formatter.d.js +30 -0
- package/lib/module/utils/formatter.d.js.map +1 -0
- package/lib/module/utils/formatter.js +217 -0
- package/lib/module/utils/formatter.js.map +1 -0
- package/lib/module/utils/parser.d.js +4 -0
- package/lib/module/utils/parser.d.js.map +1 -0
- package/lib/module/utils/parser.js +211 -0
- package/lib/module/utils/parser.js.map +1 -0
- package/lib/module/utils/styleMapper.d.js +4 -0
- package/lib/module/utils/styleMapper.d.js.map +1 -0
- package/lib/module/utils/styleMapper.js +82 -0
- package/lib/module/utils/styleMapper.js.map +1 -0
- package/lib/typescript/src/components/OverlayText.d.ts +11 -0
- package/lib/typescript/src/components/OverlayText.d.ts.map +1 -0
- package/lib/typescript/src/components/RichTextInput.d.ts +21 -0
- package/lib/typescript/src/components/RichTextInput.d.ts.map +1 -0
- package/lib/typescript/src/components/Toolbar.d.ts +13 -0
- package/lib/typescript/src/components/Toolbar.d.ts.map +1 -0
- package/lib/typescript/src/components/ToolbarButton.d.ts +8 -0
- package/lib/typescript/src/components/ToolbarButton.d.ts.map +1 -0
- package/lib/typescript/src/constants/defaultStyles.d.ts +46 -0
- package/lib/typescript/src/constants/defaultStyles.d.ts.map +1 -0
- package/lib/typescript/src/context/RichTextContext.d.ts +31 -0
- package/lib/typescript/src/context/RichTextContext.d.ts.map +1 -0
- package/lib/typescript/src/hooks/useFormatting.d.ts +26 -0
- package/lib/typescript/src/hooks/useFormatting.d.ts.map +1 -0
- package/lib/typescript/src/hooks/useRichText.d.ts +17 -0
- package/lib/typescript/src/hooks/useRichText.d.ts.map +1 -0
- package/lib/typescript/src/hooks/useSelection.d.ts +14 -0
- package/lib/typescript/src/hooks/useSelection.d.ts.map +1 -0
- package/lib/typescript/src/index.d.ts +16 -0
- package/lib/typescript/src/index.d.ts.map +1 -0
- package/lib/typescript/src/types/index.d.ts +257 -0
- package/lib/typescript/src/types/index.d.ts.map +1 -0
- package/lib/typescript/src/utils/formatter.d.ts +29 -0
- package/lib/typescript/src/utils/formatter.d.ts.map +1 -0
- package/lib/typescript/src/utils/parser.d.ts +46 -0
- package/lib/typescript/src/utils/parser.d.ts.map +1 -0
- package/lib/typescript/src/utils/styleMapper.d.ts +16 -0
- package/lib/typescript/src/utils/styleMapper.d.ts.map +1 -0
- package/package.json +1 -1
- package/src/components/OverlayText.tsx +11 -3
- package/src/components/RichTextInput.tsx +11 -5
- package/src/components/Toolbar.d.ts +1 -1
- package/src/components/Toolbar.tsx +5 -5
- package/src/components/ToolbarButton.d.ts +1 -1
- package/src/constants/defaultStyles.d.ts +1 -1
- package/src/hooks/useRichText.ts +11 -4
- package/src/index.d.ts +1 -1
- package/src/index.ts +2 -0
- package/src/types/index.d.ts +22 -10
- package/src/types/index.ts +24 -10
- package/src/utils/formatter.d.ts +2 -2
- package/src/utils/formatter.ts +4 -4
- package/src/utils/parser.d.ts +1 -1
- package/src/utils/parser.ts +2 -2
- package/src/utils/styleMapper.d.ts +1 -1
- package/src/utils/styleMapper.ts +2 -2
|
@@ -0,0 +1,221 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
Object.defineProperty(exports, "__esModule", {
|
|
4
|
+
value: true
|
|
5
|
+
});
|
|
6
|
+
exports.areStylesEqual = areStylesEqual;
|
|
7
|
+
exports.createSegment = createSegment;
|
|
8
|
+
exports.findPositionInSegments = findPositionInSegments;
|
|
9
|
+
exports.getTotalLength = getTotalLength;
|
|
10
|
+
exports.mergeAdjacentSegments = mergeAdjacentSegments;
|
|
11
|
+
exports.reconcileTextChange = reconcileTextChange;
|
|
12
|
+
exports.segmentsToPlainText = segmentsToPlainText;
|
|
13
|
+
exports.splitSegment = splitSegment;
|
|
14
|
+
var _defaultStyles = require("../constants/defaultStyles");
|
|
15
|
+
/**
|
|
16
|
+
* Creates a new segment with the given text and optional styles.
|
|
17
|
+
*/
|
|
18
|
+
function createSegment(text, styles = {
|
|
19
|
+
..._defaultStyles.EMPTY_FORMAT_STYLE
|
|
20
|
+
}) {
|
|
21
|
+
return {
|
|
22
|
+
text,
|
|
23
|
+
styles: {
|
|
24
|
+
...styles
|
|
25
|
+
}
|
|
26
|
+
};
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
/**
|
|
30
|
+
* Computes the total character length across all segments.
|
|
31
|
+
*/
|
|
32
|
+
function getTotalLength(segments) {
|
|
33
|
+
return segments.reduce((sum, seg) => sum + seg.text.length, 0);
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
/**
|
|
37
|
+
* Converts an array of segments to plain text.
|
|
38
|
+
*/
|
|
39
|
+
function segmentsToPlainText(segments) {
|
|
40
|
+
return segments.map(s => s.text).join('');
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
/**
|
|
44
|
+
* Finds which segment and character offset a global position corresponds to.
|
|
45
|
+
* Returns { segmentIndex, offsetInSegment }.
|
|
46
|
+
*/
|
|
47
|
+
function findPositionInSegments(segments, globalPosition) {
|
|
48
|
+
let remaining = globalPosition;
|
|
49
|
+
for (let i = 0; i < segments.length; i++) {
|
|
50
|
+
const segLen = segments[i].text.length;
|
|
51
|
+
if (remaining <= segLen) {
|
|
52
|
+
return {
|
|
53
|
+
segmentIndex: i,
|
|
54
|
+
offsetInSegment: remaining
|
|
55
|
+
};
|
|
56
|
+
}
|
|
57
|
+
remaining -= segLen;
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
// Position is past the end — return end of last segment
|
|
61
|
+
const lastIndex = Math.max(0, segments.length - 1);
|
|
62
|
+
return {
|
|
63
|
+
segmentIndex: lastIndex,
|
|
64
|
+
offsetInSegment: segments.length > 0 ? segments[lastIndex].text.length : 0
|
|
65
|
+
};
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
/**
|
|
69
|
+
* Splits a segment at the given offset, returning [before, after].
|
|
70
|
+
* If offset is 0 or at end, one side will have empty text.
|
|
71
|
+
*/
|
|
72
|
+
function splitSegment(segment, offset) {
|
|
73
|
+
const before = createSegment(segment.text.slice(0, offset), segment.styles);
|
|
74
|
+
const after = createSegment(segment.text.slice(offset), segment.styles);
|
|
75
|
+
return [before, after];
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
/**
|
|
79
|
+
* Checks if two FormatStyle objects are deeply equal.
|
|
80
|
+
*/
|
|
81
|
+
function areStylesEqual(a, b) {
|
|
82
|
+
return !!a.bold === !!b.bold && !!a.italic === !!b.italic && !!a.underline === !!b.underline && !!a.strikethrough === !!b.strikethrough && !!a.code === !!b.code && (a.color ?? undefined) === (b.color ?? undefined) && (a.backgroundColor ?? undefined) === (b.backgroundColor ?? undefined) && (a.fontSize ?? undefined) === (b.fontSize ?? undefined) && (a.heading ?? undefined) === (b.heading ?? undefined);
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
/**
|
|
86
|
+
* Merges adjacent segments that have identical styles.
|
|
87
|
+
* Returns a new array (does not mutate input).
|
|
88
|
+
*/
|
|
89
|
+
function mergeAdjacentSegments(segments) {
|
|
90
|
+
if (segments.length === 0) {
|
|
91
|
+
return [createSegment('')];
|
|
92
|
+
}
|
|
93
|
+
const result = [];
|
|
94
|
+
let last = null;
|
|
95
|
+
for (const seg of segments) {
|
|
96
|
+
// Empty segment → acts as boundary
|
|
97
|
+
if (seg.text.length === 0) {
|
|
98
|
+
last = null; // break merge chain
|
|
99
|
+
continue;
|
|
100
|
+
}
|
|
101
|
+
if (last && areStylesEqual(last.styles, seg.styles)) {
|
|
102
|
+
last.text += seg.text;
|
|
103
|
+
} else {
|
|
104
|
+
const newSeg = createSegment(seg.text, seg.styles);
|
|
105
|
+
result.push(newSeg);
|
|
106
|
+
last = newSeg;
|
|
107
|
+
}
|
|
108
|
+
}
|
|
109
|
+
|
|
110
|
+
// If everything was empty
|
|
111
|
+
if (result.length === 0) {
|
|
112
|
+
return [createSegment('')];
|
|
113
|
+
}
|
|
114
|
+
return result;
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
/**
|
|
118
|
+
* Given the old segments and new plain text (from TextInput onChange),
|
|
119
|
+
* reconcile the segments to preserve formatting while reflecting the text change.
|
|
120
|
+
*
|
|
121
|
+
* Strategy:
|
|
122
|
+
* 1. Find the diff region between old plain text and new plain text
|
|
123
|
+
* 2. Replace that region in the segment array
|
|
124
|
+
* 3. New text inserted at the diff point inherits the `activeStyles`
|
|
125
|
+
*/
|
|
126
|
+
function reconcileTextChange(oldSegments, newText, activeStyles) {
|
|
127
|
+
const oldText = segmentsToPlainText(oldSegments);
|
|
128
|
+
if (newText === oldText) {
|
|
129
|
+
return oldSegments;
|
|
130
|
+
}
|
|
131
|
+
|
|
132
|
+
// Find common prefix length
|
|
133
|
+
let prefixLen = 0;
|
|
134
|
+
const minLen = Math.min(oldText.length, newText.length);
|
|
135
|
+
while (prefixLen < minLen && oldText[prefixLen] === newText[prefixLen]) {
|
|
136
|
+
prefixLen++;
|
|
137
|
+
}
|
|
138
|
+
|
|
139
|
+
// Find common suffix length (from end, but not overlapping with prefix)
|
|
140
|
+
let suffixLen = 0;
|
|
141
|
+
while (suffixLen < minLen - prefixLen && oldText[oldText.length - 1 - suffixLen] === newText[newText.length - 1 - suffixLen]) {
|
|
142
|
+
suffixLen++;
|
|
143
|
+
}
|
|
144
|
+
const deleteStart = prefixLen;
|
|
145
|
+
const deleteEnd = oldText.length - suffixLen;
|
|
146
|
+
const insertedText = newText.slice(prefixLen, newText.length - suffixLen);
|
|
147
|
+
|
|
148
|
+
// Build new segments
|
|
149
|
+
// 1. Keep segments before deleteStart
|
|
150
|
+
// 2. Insert new text segment with activeStyles
|
|
151
|
+
// 3. Keep segments after deleteEnd
|
|
152
|
+
|
|
153
|
+
const result = [];
|
|
154
|
+
let pos = 0;
|
|
155
|
+
let phase = 'before';
|
|
156
|
+
let insertedNewSegment = false;
|
|
157
|
+
for (const seg of oldSegments) {
|
|
158
|
+
const segStart = pos;
|
|
159
|
+
const segEnd = pos + seg.text.length;
|
|
160
|
+
if (phase === 'before') {
|
|
161
|
+
if (segEnd <= deleteStart) {
|
|
162
|
+
// Entire segment is before delete region
|
|
163
|
+
result.push(createSegment(seg.text, seg.styles));
|
|
164
|
+
} else if (segStart < deleteStart) {
|
|
165
|
+
// Segment partially before delete region
|
|
166
|
+
result.push(createSegment(seg.text.slice(0, deleteStart - segStart), seg.styles));
|
|
167
|
+
if (!insertedNewSegment && insertedText.length > 0) {
|
|
168
|
+
result.push(createSegment(insertedText, activeStyles));
|
|
169
|
+
insertedNewSegment = true;
|
|
170
|
+
}
|
|
171
|
+
if (segEnd > deleteEnd) {
|
|
172
|
+
// Segment also extends past delete region
|
|
173
|
+
result.push(createSegment(seg.text.slice(deleteEnd - segStart), seg.styles));
|
|
174
|
+
phase = 'after';
|
|
175
|
+
} else {
|
|
176
|
+
phase = 'during';
|
|
177
|
+
}
|
|
178
|
+
} else {
|
|
179
|
+
// segStart >= deleteStart → we've reached the delete region
|
|
180
|
+
if (!insertedNewSegment && insertedText.length > 0) {
|
|
181
|
+
result.push(createSegment(insertedText, activeStyles));
|
|
182
|
+
insertedNewSegment = true;
|
|
183
|
+
}
|
|
184
|
+
if (segEnd <= deleteEnd) {
|
|
185
|
+
// Entire segment is within delete region — skip it
|
|
186
|
+
phase = segEnd === deleteEnd ? 'after' : 'during';
|
|
187
|
+
} else {
|
|
188
|
+
// Segment extends past delete region
|
|
189
|
+
result.push(createSegment(seg.text.slice(deleteEnd - segStart), seg.styles));
|
|
190
|
+
phase = 'after';
|
|
191
|
+
}
|
|
192
|
+
}
|
|
193
|
+
} else if (phase === 'during') {
|
|
194
|
+
if (!insertedNewSegment && insertedText.length > 0) {
|
|
195
|
+
result.push(createSegment(insertedText, activeStyles));
|
|
196
|
+
insertedNewSegment = true;
|
|
197
|
+
}
|
|
198
|
+
if (segEnd <= deleteEnd) {
|
|
199
|
+
// Still in delete region — skip
|
|
200
|
+
if (segEnd === deleteEnd) {
|
|
201
|
+
phase = 'after';
|
|
202
|
+
}
|
|
203
|
+
} else {
|
|
204
|
+
// Segment extends past delete region
|
|
205
|
+
result.push(createSegment(seg.text.slice(deleteEnd - segStart), seg.styles));
|
|
206
|
+
phase = 'after';
|
|
207
|
+
}
|
|
208
|
+
} else {
|
|
209
|
+
// phase === 'after'
|
|
210
|
+
result.push(createSegment(seg.text, seg.styles));
|
|
211
|
+
}
|
|
212
|
+
pos = segEnd;
|
|
213
|
+
}
|
|
214
|
+
|
|
215
|
+
// If we never inserted the new text (e.g., appending at end)
|
|
216
|
+
if (!insertedNewSegment && insertedText.length > 0) {
|
|
217
|
+
result.push(createSegment(insertedText, activeStyles));
|
|
218
|
+
}
|
|
219
|
+
return mergeAdjacentSegments(result);
|
|
220
|
+
}
|
|
221
|
+
//# sourceMappingURL=parser.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"names":["_defaultStyles","require","createSegment","text","styles","EMPTY_FORMAT_STYLE","getTotalLength","segments","reduce","sum","seg","length","segmentsToPlainText","map","s","join","findPositionInSegments","globalPosition","remaining","i","segLen","segmentIndex","offsetInSegment","lastIndex","Math","max","splitSegment","segment","offset","before","slice","after","areStylesEqual","a","b","bold","italic","underline","strikethrough","code","color","undefined","backgroundColor","fontSize","heading","mergeAdjacentSegments","result","last","newSeg","push","reconcileTextChange","oldSegments","newText","activeStyles","oldText","prefixLen","minLen","min","suffixLen","deleteStart","deleteEnd","insertedText","pos","phase","insertedNewSegment","segStart","segEnd"],"sourceRoot":"../../../src","sources":["utils/parser.ts"],"mappings":"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","ignoreList":[]}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"names":[],"sourceRoot":"../../../src","sources":["utils/styleMapper.d.ts"],"mappings":"","ignoreList":[]}
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
Object.defineProperty(exports, "__esModule", {
|
|
4
|
+
value: true
|
|
5
|
+
});
|
|
6
|
+
exports.formatStyleToTextStyle = formatStyleToTextStyle;
|
|
7
|
+
exports.segmentToTextStyle = segmentToTextStyle;
|
|
8
|
+
exports.segmentsToTextStyles = segmentsToTextStyles;
|
|
9
|
+
var _defaultStyles = require("../constants/defaultStyles");
|
|
10
|
+
/**
|
|
11
|
+
* Maps a FormatStyle to a React Native TextStyle.
|
|
12
|
+
* Applies formatting properties based on the segment's style.
|
|
13
|
+
*/
|
|
14
|
+
function formatStyleToTextStyle(formatStyle, theme) {
|
|
15
|
+
const resolvedTheme = theme ?? _defaultStyles.DEFAULT_THEME;
|
|
16
|
+
const style = {};
|
|
17
|
+
|
|
18
|
+
// Bold
|
|
19
|
+
if (formatStyle.bold) {
|
|
20
|
+
style.fontWeight = 'bold';
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
// Italic
|
|
24
|
+
if (formatStyle.italic) {
|
|
25
|
+
style.fontStyle = 'italic';
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
// Underline and strikethrough
|
|
29
|
+
if (formatStyle.underline && formatStyle.strikethrough) {
|
|
30
|
+
style.textDecorationLine = 'underline line-through';
|
|
31
|
+
} else if (formatStyle.underline) {
|
|
32
|
+
style.textDecorationLine = 'underline';
|
|
33
|
+
} else if (formatStyle.strikethrough) {
|
|
34
|
+
style.textDecorationLine = 'line-through';
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
// Code — apply monospace font and background
|
|
38
|
+
if (formatStyle.code) {
|
|
39
|
+
const codeStyle = resolvedTheme.codeStyle ?? _defaultStyles.DEFAULT_THEME.codeStyle;
|
|
40
|
+
if (codeStyle) {
|
|
41
|
+
Object.assign(style, codeStyle);
|
|
42
|
+
}
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
// Text color
|
|
46
|
+
if (formatStyle.color) {
|
|
47
|
+
style.color = formatStyle.color;
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
// Background color
|
|
51
|
+
if (formatStyle.backgroundColor) {
|
|
52
|
+
style.backgroundColor = formatStyle.backgroundColor;
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
// Font size
|
|
56
|
+
if (formatStyle.fontSize) {
|
|
57
|
+
style.fontSize = formatStyle.fontSize;
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
// Heading — overrides font size and weight
|
|
61
|
+
if (formatStyle.heading && formatStyle.heading !== 'none') {
|
|
62
|
+
style.fontSize = _defaultStyles.HEADING_FONT_SIZES[formatStyle.heading];
|
|
63
|
+
style.fontWeight = 'bold';
|
|
64
|
+
style.lineHeight = _defaultStyles.HEADING_FONT_SIZES[formatStyle.heading] * 1.3;
|
|
65
|
+
}
|
|
66
|
+
return style;
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
/**
|
|
70
|
+
* Maps an entire segment to its computed TextStyle (base + format).
|
|
71
|
+
*/
|
|
72
|
+
function segmentToTextStyle(segment, theme) {
|
|
73
|
+
const baseStyle = theme?.baseTextStyle ?? _defaultStyles.DEFAULT_THEME.baseTextStyle ?? {};
|
|
74
|
+
const formatStyle = formatStyleToTextStyle(segment.styles, theme);
|
|
75
|
+
return {
|
|
76
|
+
...baseStyle,
|
|
77
|
+
...formatStyle
|
|
78
|
+
};
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
/**
|
|
82
|
+
* Batch-maps an array of segments to an array of TextStyles.
|
|
83
|
+
*/
|
|
84
|
+
function segmentsToTextStyles(segments, theme) {
|
|
85
|
+
return segments.map(seg => segmentToTextStyle(seg, theme));
|
|
86
|
+
}
|
|
87
|
+
//# sourceMappingURL=styleMapper.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"names":["_defaultStyles","require","formatStyleToTextStyle","formatStyle","theme","resolvedTheme","DEFAULT_THEME","style","bold","fontWeight","italic","fontStyle","underline","strikethrough","textDecorationLine","code","codeStyle","Object","assign","color","backgroundColor","fontSize","heading","HEADING_FONT_SIZES","lineHeight","segmentToTextStyle","segment","baseStyle","baseTextStyle","styles","segmentsToTextStyles","segments","map","seg"],"sourceRoot":"../../../src","sources":["utils/styleMapper.ts"],"mappings":";;;;;;;;AAEA,IAAAA,cAAA,GAAAC,OAAA;AAEA;AACA;AACA;AACA;AACO,SAASC,sBAAsBA,CACpCC,WAAwB,EACxBC,KAAqB,EACV;EACX,MAAMC,aAAa,GAAGD,KAAK,IAAIE,4BAAa;EAC5C,MAAMC,KAAgB,GAAG,CAAC,CAAC;;EAE3B;EACA,IAAIJ,WAAW,CAACK,IAAI,EAAE;IACpBD,KAAK,CAACE,UAAU,GAAG,MAAM;EAC3B;;EAEA;EACA,IAAIN,WAAW,CAACO,MAAM,EAAE;IACtBH,KAAK,CAACI,SAAS,GAAG,QAAQ;EAC5B;;EAEA;EACA,IAAIR,WAAW,CAACS,SAAS,IAAIT,WAAW,CAACU,aAAa,EAAE;IACtDN,KAAK,CAACO,kBAAkB,GAAG,wBAAwB;EACrD,CAAC,MAAM,IAAIX,WAAW,CAACS,SAAS,EAAE;IAChCL,KAAK,CAACO,kBAAkB,GAAG,WAAW;EACxC,CAAC,MAAM,IAAIX,WAAW,CAACU,aAAa,EAAE;IACpCN,KAAK,CAACO,kBAAkB,GAAG,cAAc;EAC3C;;EAEA;EACA,IAAIX,WAAW,CAACY,IAAI,EAAE;IACpB,MAAMC,SAAS,GAAGX,aAAa,CAACW,SAAS,IAAIV,4BAAa,CAACU,SAAS;IACpE,IAAIA,SAAS,EAAE;MACbC,MAAM,CAACC,MAAM,CAACX,KAAK,EAAES,SAAS,CAAC;IACjC;EACF;;EAEA;EACA,IAAIb,WAAW,CAACgB,KAAK,EAAE;IACrBZ,KAAK,CAACY,KAAK,GAAGhB,WAAW,CAACgB,KAAK;EACjC;;EAEA;EACA,IAAIhB,WAAW,CAACiB,eAAe,EAAE;IAC/Bb,KAAK,CAACa,eAAe,GAAGjB,WAAW,CAACiB,eAAe;EACrD;;EAEA;EACA,IAAIjB,WAAW,CAACkB,QAAQ,EAAE;IACxBd,KAAK,CAACc,QAAQ,GAAGlB,WAAW,CAACkB,QAAQ;EACvC;;EAEA;EACA,IAAIlB,WAAW,CAACmB,OAAO,IAAInB,WAAW,CAACmB,OAAO,KAAK,MAAM,EAAE;IACzDf,KAAK,CAACc,QAAQ,GAAGE,iCAAkB,CAACpB,WAAW,CAACmB,OAAO,CAAC;IACxDf,KAAK,CAACE,UAAU,GAAG,MAAM;IACzBF,KAAK,CAACiB,UAAU,GAAGD,iCAAkB,CAACpB,WAAW,CAACmB,OAAO,CAAC,GAAG,GAAG;EAClE;EAEA,OAAOf,KAAK;AACd;;AAEA;AACA;AACA;AACO,SAASkB,kBAAkBA,CAChCC,OAAsB,EACtBtB,KAAqB,EACV;EACX,MAAMuB,SAAS,GAAGvB,KAAK,EAAEwB,aAAa,IAAItB,4BAAa,CAACsB,aAAa,IAAI,CAAC,CAAC;EAC3E,MAAMzB,WAAW,GAAGD,sBAAsB,CAACwB,OAAO,CAACG,MAAM,EAAEzB,KAAK,CAAC;EAEjE,OAAO;IACL,GAAGuB,SAAS;IACZ,GAAGxB;EACL,CAAC;AACH;;AAEA;AACA;AACA;AACO,SAAS2B,oBAAoBA,CAClCC,QAAyB,EACzB3B,KAAqB,EACR;EACb,OAAO2B,QAAQ,CAACC,GAAG,CAAEC,GAAG,IAAKR,kBAAkB,CAACQ,GAAG,EAAE7B,KAAK,CAAC,CAAC;AAC9D","ignoreList":[]}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"names":[],"sourceRoot":"../../../src","sources":["components/OverlayText.d.ts"],"mappings":"","ignoreList":[]}
|
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
import React from 'react';
|
|
4
|
+
import { Text, View } from 'react-native';
|
|
5
|
+
import { segmentToTextStyle } from '../utils/styleMapper';
|
|
6
|
+
import { DEFAULT_THEME } from '../constants/defaultStyles';
|
|
7
|
+
|
|
8
|
+
/**
|
|
9
|
+
* OverlayText renders the styled text segments as a `<Text>` component tree.
|
|
10
|
+
*
|
|
11
|
+
* This component is positioned behind the transparent TextInput to create
|
|
12
|
+
* the overlay effect — the user types into the TextInput while seeing
|
|
13
|
+
* the formatted rendering from this component.
|
|
14
|
+
*/
|
|
15
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
16
|
+
export const OverlayText = /*#__PURE__*/React.memo(({
|
|
17
|
+
segments,
|
|
18
|
+
baseTextStyle,
|
|
19
|
+
theme
|
|
20
|
+
}) => {
|
|
21
|
+
const resolvedTheme = theme ?? DEFAULT_THEME;
|
|
22
|
+
const overlayStyle = resolvedTheme.overlayContainerStyle ?? DEFAULT_THEME.overlayContainerStyle;
|
|
23
|
+
const resolvedBaseTextStyle = baseTextStyle ?? resolvedTheme.baseTextStyle ?? DEFAULT_THEME.baseTextStyle;
|
|
24
|
+
const overlayTheme = {
|
|
25
|
+
...resolvedTheme,
|
|
26
|
+
baseTextStyle: resolvedBaseTextStyle
|
|
27
|
+
};
|
|
28
|
+
return /*#__PURE__*/_jsx(View, {
|
|
29
|
+
style: overlayStyle,
|
|
30
|
+
pointerEvents: "none",
|
|
31
|
+
children: /*#__PURE__*/_jsx(Text, {
|
|
32
|
+
style: resolvedBaseTextStyle,
|
|
33
|
+
children: segments.map((segment, index) => {
|
|
34
|
+
if (segment.text.length === 0 && segments.length > 1) {
|
|
35
|
+
return null;
|
|
36
|
+
}
|
|
37
|
+
const textStyle = segmentToTextStyle(segment, overlayTheme);
|
|
38
|
+
return /*#__PURE__*/_jsx(Text, {
|
|
39
|
+
style: textStyle,
|
|
40
|
+
children: segment.text
|
|
41
|
+
}, `${index}-${segment.text.slice(0, 8)}`);
|
|
42
|
+
})
|
|
43
|
+
})
|
|
44
|
+
});
|
|
45
|
+
});
|
|
46
|
+
OverlayText.displayName = 'OverlayText';
|
|
47
|
+
//# sourceMappingURL=OverlayText.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"names":["React","Text","View","segmentToTextStyle","DEFAULT_THEME","jsx","_jsx","OverlayText","memo","segments","baseTextStyle","theme","resolvedTheme","overlayStyle","overlayContainerStyle","resolvedBaseTextStyle","overlayTheme","style","pointerEvents","children","map","segment","index","text","length","textStyle","slice","displayName"],"sourceRoot":"../../../src","sources":["components/OverlayText.tsx"],"mappings":";;AAAA,OAAOA,KAAK,MAAM,OAAO;AACzB,SAASC,IAAI,EAAEC,IAAI,QAAQ,cAAc;AAEzC,SAASC,kBAAkB,QAAQ,sBAAsB;AACzD,SAASC,aAAa,QAAQ,4BAA4B;;AAE1D;AACA;AACA;AACA;AACA;AACA;AACA;AANA,SAAAC,GAAA,IAAAC,IAAA;AAOA,OAAO,MAAMC,WAAuC,gBAAGP,KAAK,CAACQ,IAAI,CAC/D,CAAC;EAAEC,QAAQ;EAAEC,aAAa;EAAEC;AAAM,CAAC,KAAK;EACtC,MAAMC,aAAa,GAAGD,KAAK,IAAIP,aAAa;EAC5C,MAAMS,YAAY,GAChBD,aAAa,CAACE,qBAAqB,IACnCV,aAAa,CAACU,qBAAqB;EACrC,MAAMC,qBAAqB,GACzBL,aAAa,IACbE,aAAa,CAACF,aAAa,IAC3BN,aAAa,CAACM,aAAa;EAC7B,MAAMM,YAAY,GAAG;IACnB,GAAGJ,aAAa;IAChBF,aAAa,EAAEK;EACjB,CAAC;EAED,oBACET,IAAA,CAACJ,IAAI;IAACe,KAAK,EAAEJ,YAAa;IAACK,aAAa,EAAC,MAAM;IAAAC,QAAA,eAC7Cb,IAAA,CAACL,IAAI;MAACgB,KAAK,EAAEF,qBAAsB;MAAAI,QAAA,EAChCV,QAAQ,CAACW,GAAG,CAAC,CAACC,OAAO,EAAEC,KAAK,KAAK;QAChC,IAAID,OAAO,CAACE,IAAI,CAACC,MAAM,KAAK,CAAC,IAAIf,QAAQ,CAACe,MAAM,GAAG,CAAC,EAAE;UACpD,OAAO,IAAI;QACb;QAEA,MAAMC,SAAS,GAAGtB,kBAAkB,CAACkB,OAAO,EAAEL,YAAY,CAAC;QAE3D,oBACEV,IAAA,CAACL,IAAI;UAEHgB,KAAK,EAAEQ,SAAU;UAAAN,QAAA,EAEhBE,OAAO,CAACE;QAAI,GAHR,GAAGD,KAAK,IAAID,OAAO,CAACE,IAAI,CAACG,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,EAIrC,CAAC;MAEX,CAAC;IAAC,CACE;EAAC,CACH,CAAC;AAEX,CACF,CAAC;AAEDnB,WAAW,CAACoB,WAAW,GAAG,aAAa","ignoreList":[]}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"names":[],"sourceRoot":"../../../src","sources":["components/RichTextInput.d.ts"],"mappings":"","ignoreList":[]}
|
|
@@ -0,0 +1,158 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
import React, { useEffect, useCallback } from 'react';
|
|
4
|
+
import { View, TextInput, StyleSheet } from 'react-native';
|
|
5
|
+
import { DEFAULT_THEME } from '../constants/defaultStyles';
|
|
6
|
+
import { segmentsToPlainText } from '../utils/parser';
|
|
7
|
+
import { useRichText } from '../hooks/useRichText';
|
|
8
|
+
import { OverlayText } from './OverlayText';
|
|
9
|
+
import { Toolbar } from './Toolbar';
|
|
10
|
+
|
|
11
|
+
/**
|
|
12
|
+
* RichTextInput — The main rich text editor component.
|
|
13
|
+
*
|
|
14
|
+
* Uses the Overlay Technique:
|
|
15
|
+
* - A transparent `TextInput` on top captures user input and selection
|
|
16
|
+
* - A styled `<Text>` layer behind it renders the formatted content
|
|
17
|
+
* - Both share identical font metrics for pixel-perfect alignment
|
|
18
|
+
*
|
|
19
|
+
* @example
|
|
20
|
+
* ```tsx
|
|
21
|
+
* <RichTextInput
|
|
22
|
+
* placeholder="Start typing..."
|
|
23
|
+
* showToolbar
|
|
24
|
+
* onChangeSegments={(segments) => console.log(segments)}
|
|
25
|
+
* />
|
|
26
|
+
* ```
|
|
27
|
+
*/
|
|
28
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
29
|
+
export const RichTextInput = ({
|
|
30
|
+
initialSegments,
|
|
31
|
+
onChangeSegments,
|
|
32
|
+
onChangeText,
|
|
33
|
+
placeholder = 'Start typing...',
|
|
34
|
+
editable = true,
|
|
35
|
+
maxLength,
|
|
36
|
+
showToolbar = true,
|
|
37
|
+
toolbarPosition = 'top',
|
|
38
|
+
toolbarItems,
|
|
39
|
+
theme,
|
|
40
|
+
multiline = true,
|
|
41
|
+
minHeight = 120,
|
|
42
|
+
maxHeight,
|
|
43
|
+
autoFocus = false,
|
|
44
|
+
textInputProps,
|
|
45
|
+
renderToolbar,
|
|
46
|
+
onReady
|
|
47
|
+
}) => {
|
|
48
|
+
const resolvedTheme = theme ?? DEFAULT_THEME;
|
|
49
|
+
const {
|
|
50
|
+
state,
|
|
51
|
+
actions
|
|
52
|
+
} = useRichText({
|
|
53
|
+
initialSegments,
|
|
54
|
+
onChangeSegments,
|
|
55
|
+
onChangeText
|
|
56
|
+
});
|
|
57
|
+
|
|
58
|
+
// Expose actions via onReady callback
|
|
59
|
+
useEffect(() => {
|
|
60
|
+
onReady?.(actions);
|
|
61
|
+
}, [onReady, actions]);
|
|
62
|
+
|
|
63
|
+
// Build plain text for the TextInput value
|
|
64
|
+
const plainText = segmentsToPlainText(state.segments);
|
|
65
|
+
|
|
66
|
+
// Handle selection change from TextInput
|
|
67
|
+
const onSelectionChange = useCallback(e => {
|
|
68
|
+
const {
|
|
69
|
+
start,
|
|
70
|
+
end
|
|
71
|
+
} = e.nativeEvent.selection;
|
|
72
|
+
actions.handleSelectionChange({
|
|
73
|
+
start,
|
|
74
|
+
end
|
|
75
|
+
});
|
|
76
|
+
}, [actions]);
|
|
77
|
+
|
|
78
|
+
// Container style
|
|
79
|
+
const containerStyle = [resolvedTheme.containerStyle ?? DEFAULT_THEME.containerStyle];
|
|
80
|
+
|
|
81
|
+
// Input area style
|
|
82
|
+
const inputAreaStyle = [styles.inputArea, {
|
|
83
|
+
minHeight
|
|
84
|
+
}, maxHeight ? {
|
|
85
|
+
maxHeight
|
|
86
|
+
} : undefined];
|
|
87
|
+
|
|
88
|
+
// Input style
|
|
89
|
+
const inputStyle = [styles.textInput, resolvedTheme.baseTextStyle ?? DEFAULT_THEME.baseTextStyle, resolvedTheme.inputStyle ?? DEFAULT_THEME.inputStyle, textInputProps?.style, styles.hiddenInputText];
|
|
90
|
+
|
|
91
|
+
// Toolbar component
|
|
92
|
+
const toolbarComponent = showToolbar ? /*#__PURE__*/_jsx(Toolbar, {
|
|
93
|
+
actions: actions,
|
|
94
|
+
state: state,
|
|
95
|
+
items: toolbarItems,
|
|
96
|
+
theme: resolvedTheme,
|
|
97
|
+
renderToolbar: renderToolbar
|
|
98
|
+
}) : null;
|
|
99
|
+
|
|
100
|
+
// Toolbar border
|
|
101
|
+
const toolbarBorderStyle = toolbarPosition === 'top' ? {
|
|
102
|
+
borderBottomWidth: 1,
|
|
103
|
+
borderBottomColor: resolvedTheme.colors?.toolbarBorder ?? DEFAULT_THEME.colors?.toolbarBorder
|
|
104
|
+
} : {
|
|
105
|
+
borderTopWidth: 1,
|
|
106
|
+
borderTopColor: resolvedTheme.colors?.toolbarBorder ?? DEFAULT_THEME.colors?.toolbarBorder
|
|
107
|
+
};
|
|
108
|
+
return /*#__PURE__*/_jsxs(View, {
|
|
109
|
+
style: containerStyle,
|
|
110
|
+
children: [toolbarPosition === 'top' && toolbarComponent && /*#__PURE__*/_jsx(View, {
|
|
111
|
+
style: toolbarBorderStyle,
|
|
112
|
+
children: toolbarComponent
|
|
113
|
+
}), /*#__PURE__*/_jsxs(View, {
|
|
114
|
+
style: inputAreaStyle,
|
|
115
|
+
children: [/*#__PURE__*/_jsx(OverlayText, {
|
|
116
|
+
segments: state.segments,
|
|
117
|
+
baseTextStyle: resolvedTheme.baseTextStyle,
|
|
118
|
+
theme: resolvedTheme
|
|
119
|
+
}), /*#__PURE__*/_jsx(TextInput, {
|
|
120
|
+
...textInputProps,
|
|
121
|
+
style: inputStyle,
|
|
122
|
+
value: plainText,
|
|
123
|
+
onChangeText: actions.handleTextChange,
|
|
124
|
+
onSelectionChange: onSelectionChange,
|
|
125
|
+
multiline: multiline,
|
|
126
|
+
placeholder: placeholder,
|
|
127
|
+
placeholderTextColor: resolvedTheme.colors?.placeholder ?? DEFAULT_THEME.colors?.placeholder,
|
|
128
|
+
editable: editable,
|
|
129
|
+
maxLength: maxLength,
|
|
130
|
+
autoFocus: autoFocus,
|
|
131
|
+
underlineColorAndroid: "transparent",
|
|
132
|
+
selectionColor: resolvedTheme.colors?.cursor ?? DEFAULT_THEME.colors?.cursor,
|
|
133
|
+
textAlignVertical: "top",
|
|
134
|
+
scrollEnabled: typeof maxHeight === 'number'
|
|
135
|
+
})]
|
|
136
|
+
}), toolbarPosition === 'bottom' && toolbarComponent && /*#__PURE__*/_jsx(View, {
|
|
137
|
+
style: toolbarBorderStyle,
|
|
138
|
+
children: toolbarComponent
|
|
139
|
+
})]
|
|
140
|
+
});
|
|
141
|
+
};
|
|
142
|
+
RichTextInput.displayName = 'RichTextInput';
|
|
143
|
+
const styles = StyleSheet.create({
|
|
144
|
+
inputArea: {
|
|
145
|
+
position: 'relative'
|
|
146
|
+
},
|
|
147
|
+
textInput: {
|
|
148
|
+
position: 'relative',
|
|
149
|
+
zIndex: 1
|
|
150
|
+
},
|
|
151
|
+
hiddenInputText: {
|
|
152
|
+
// Keep the editable layer invisible while preserving the caret.
|
|
153
|
+
color: 'transparent',
|
|
154
|
+
backgroundColor: 'transparent',
|
|
155
|
+
textShadowColor: 'transparent'
|
|
156
|
+
}
|
|
157
|
+
});
|
|
158
|
+
//# sourceMappingURL=RichTextInput.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"names":["React","useEffect","useCallback","View","TextInput","StyleSheet","DEFAULT_THEME","segmentsToPlainText","useRichText","OverlayText","Toolbar","jsx","_jsx","jsxs","_jsxs","RichTextInput","initialSegments","onChangeSegments","onChangeText","placeholder","editable","maxLength","showToolbar","toolbarPosition","toolbarItems","theme","multiline","minHeight","maxHeight","autoFocus","textInputProps","renderToolbar","onReady","resolvedTheme","state","actions","plainText","segments","onSelectionChange","e","start","end","nativeEvent","selection","handleSelectionChange","containerStyle","inputAreaStyle","styles","inputArea","undefined","inputStyle","textInput","baseTextStyle","style","hiddenInputText","toolbarComponent","items","toolbarBorderStyle","borderBottomWidth","borderBottomColor","colors","toolbarBorder","borderTopWidth","borderTopColor","children","value","handleTextChange","placeholderTextColor","underlineColorAndroid","selectionColor","cursor","textAlignVertical","scrollEnabled","displayName","create","position","zIndex","color","backgroundColor","textShadowColor"],"sourceRoot":"../../../src","sources":["components/RichTextInput.tsx"],"mappings":";;AAAA,OAAOA,KAAK,IAAIC,SAAS,EAAEC,WAAW,QAAQ,OAAO;AACrD,SACEC,IAAI,EACJC,SAAS,EACTC,UAAU,QAGL,cAAc;AAErB,SAASC,aAAa,QAAQ,4BAA4B;AAC1D,SAASC,mBAAmB,QAAQ,iBAAiB;AACrD,SAASC,WAAW,QAAQ,sBAAsB;AAClD,SAASC,WAAW,QAAQ,eAAe;AAC3C,SAASC,OAAO,QAAQ,WAAW;;AAEnC;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AAhBA,SAAAC,GAAA,IAAAC,IAAA,EAAAC,IAAA,IAAAC,KAAA;AAiBA,OAAO,MAAMC,aAA2C,GAAGA,CAAC;EAC1DC,eAAe;EACfC,gBAAgB;EAChBC,YAAY;EACZC,WAAW,GAAG,iBAAiB;EAC/BC,QAAQ,GAAG,IAAI;EACfC,SAAS;EACTC,WAAW,GAAG,IAAI;EAClBC,eAAe,GAAG,KAAK;EACvBC,YAAY;EACZC,KAAK;EACLC,SAAS,GAAG,IAAI;EAChBC,SAAS,GAAG,GAAG;EACfC,SAAS;EACTC,SAAS,GAAG,KAAK;EACjBC,cAAc;EACdC,aAAa;EACbC;AACF,CAAC,KAAK;EACJ,MAAMC,aAAa,GAAGR,KAAK,IAAInB,aAAa;EAE5C,MAAM;IAAE4B,KAAK;IAAEC;EAAQ,CAAC,GAAG3B,WAAW,CAAC;IACrCQ,eAAe;IACfC,gBAAgB;IAChBC;EACF,CAAC,CAAC;;EAEF;EACAjB,SAAS,CAAC,MAAM;IACd+B,OAAO,GAAGG,OAAO,CAAC;EACpB,CAAC,EAAE,CAACH,OAAO,EAAEG,OAAO,CAAC,CAAC;;EAEtB;EACA,MAAMC,SAAS,GAAG7B,mBAAmB,CAAC2B,KAAK,CAACG,QAAQ,CAAC;;EAErD;EACA,MAAMC,iBAAiB,GAAGpC,WAAW,CAClCqC,CAA0D,IAAK;IAC9D,MAAM;MAAEC,KAAK;MAAEC;IAAI,CAAC,GAAGF,CAAC,CAACG,WAAW,CAACC,SAAS;IAC9CR,OAAO,CAACS,qBAAqB,CAAC;MAAEJ,KAAK;MAAEC;IAAI,CAAC,CAAC;EAC/C,CAAC,EACD,CAACN,OAAO,CACV,CAAC;;EAED;EACA,MAAMU,cAAc,GAAG,CACrBZ,aAAa,CAACY,cAAc,IAAIvC,aAAa,CAACuC,cAAc,CAC7D;;EAED;EACA,MAAMC,cAAc,GAAG,CACrBC,MAAM,CAACC,SAAS,EAChB;IAAErB;EAAU,CAAC,EACbC,SAAS,GAAG;IAAEA;EAAU,CAAC,GAAGqB,SAAS,CACtC;;EAED;EACA,MAAMC,UAAU,GAAG,CACjBH,MAAM,CAACI,SAAS,EAChBlB,aAAa,CAACmB,aAAa,IAAI9C,aAAa,CAAC8C,aAAa,EAC1DnB,aAAa,CAACiB,UAAU,IAAI5C,aAAa,CAAC4C,UAAU,EACpDpB,cAAc,EAAEuB,KAAK,EACrBN,MAAM,CAACO,eAAe,CACvB;;EAED;EACA,MAAMC,gBAAgB,GAAGjC,WAAW,gBAClCV,IAAA,CAACF,OAAO;IACNyB,OAAO,EAAEA,OAAQ;IACjBD,KAAK,EAAEA,KAAM;IACbsB,KAAK,EAAEhC,YAAa;IACpBC,KAAK,EAAEQ,aAAc;IACrBF,aAAa,EAAEA;EAAc,CAC9B,CAAC,GACA,IAAI;;EAER;EACA,MAAM0B,kBAAkB,GACtBlC,eAAe,KAAK,KAAK,GACrB;IAAEmC,iBAAiB,EAAE,CAAC;IAAEC,iBAAiB,EAAE1B,aAAa,CAAC2B,MAAM,EAAEC,aAAa,IAAIvD,aAAa,CAACsD,MAAM,EAAEC;EAAc,CAAC,GACvH;IAAEC,cAAc,EAAE,CAAC;IAAEC,cAAc,EAAE9B,aAAa,CAAC2B,MAAM,EAAEC,aAAa,IAAIvD,aAAa,CAACsD,MAAM,EAAEC;EAAc,CAAC;EAEvH,oBACE/C,KAAA,CAACX,IAAI;IAACkD,KAAK,EAAER,cAAe;IAAAmB,QAAA,GAEzBzC,eAAe,KAAK,KAAK,IAAIgC,gBAAgB,iBAC5C3C,IAAA,CAACT,IAAI;MAACkD,KAAK,EAAEI,kBAAmB;MAAAO,QAAA,EAAET;IAAgB,CAAO,CAC1D,eAGDzC,KAAA,CAACX,IAAI;MAACkD,KAAK,EAAEP,cAAe;MAAAkB,QAAA,gBAE1BpD,IAAA,CAACH,WAAW;QACV4B,QAAQ,EAAEH,KAAK,CAACG,QAAS;QACzBe,aAAa,EAAEnB,aAAa,CAACmB,aAAc;QAC3C3B,KAAK,EAAEQ;MAAc,CACtB,CAAC,eAGFrB,IAAA,CAACR,SAAS;QAAA,GACJ0B,cAAc;QAClBuB,KAAK,EAAEH,UAAW;QAClBe,KAAK,EAAE7B,SAAU;QACjBlB,YAAY,EAAEiB,OAAO,CAAC+B,gBAAiB;QACvC5B,iBAAiB,EAAEA,iBAAkB;QACrCZ,SAAS,EAAEA,SAAU;QACrBP,WAAW,EAAEA,WAAY;QACzBgD,oBAAoB,EAClBlC,aAAa,CAAC2B,MAAM,EAAEzC,WAAW,IACjCb,aAAa,CAACsD,MAAM,EAAEzC,WACvB;QACDC,QAAQ,EAAEA,QAAS;QACnBC,SAAS,EAAEA,SAAU;QACrBQ,SAAS,EAAEA,SAAU;QACrBuC,qBAAqB,EAAC,aAAa;QACnCC,cAAc,EACZpC,aAAa,CAAC2B,MAAM,EAAEU,MAAM,IAAIhE,aAAa,CAACsD,MAAM,EAAEU,MACvD;QACDC,iBAAiB,EAAC,KAAK;QACvBC,aAAa,EAAE,OAAO5C,SAAS,KAAK;MAAS,CAC9C,CAAC;IAAA,CACE,CAAC,EAGNL,eAAe,KAAK,QAAQ,IAAIgC,gBAAgB,iBAC/C3C,IAAA,CAACT,IAAI;MAACkD,KAAK,EAAEI,kBAAmB;MAAAO,QAAA,EAAET;IAAgB,CAAO,CAC1D;EAAA,CACG,CAAC;AAEX,CAAC;AAEDxC,aAAa,CAAC0D,WAAW,GAAG,eAAe;AAE3C,MAAM1B,MAAM,GAAG1C,UAAU,CAACqE,MAAM,CAAC;EAC/B1B,SAAS,EAAE;IACT2B,QAAQ,EAAE;EACZ,CAAC;EACDxB,SAAS,EAAE;IACTwB,QAAQ,EAAE,UAAU;IACpBC,MAAM,EAAE;EACV,CAAC;EACDtB,eAAe,EAAE;IACf;IACAuB,KAAK,EAAE,aAAa;IACpBC,eAAe,EAAE,aAAa;IAC9BC,eAAe,EAAE;EACnB;AACF,CAAC,CAAC","ignoreList":[]}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"names":[],"sourceRoot":"../../../src","sources":["components/Toolbar.d.ts"],"mappings":"","ignoreList":[]}
|