tycho-components 0.41.7 → 0.42.1
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.
|
@@ -11,8 +11,12 @@ export type Chunk = {
|
|
|
11
11
|
f: number;
|
|
12
12
|
l: number;
|
|
13
13
|
t: string;
|
|
14
|
+
/** Stable chunk identity (4-char alphanumeric), mirrors token `tid`. */
|
|
15
|
+
kid?: string;
|
|
14
16
|
coidx?: number[];
|
|
15
17
|
ep?: boolean;
|
|
18
|
+
/** Runtime: empty-category phrase node. */
|
|
19
|
+
empty?: boolean;
|
|
16
20
|
};
|
|
17
21
|
export type Token = {
|
|
18
22
|
p: number;
|
|
@@ -109,8 +109,9 @@ export function shouldSkipJunctionContinuationElement(elements, index, selectedT
|
|
|
109
109
|
if (element.type === PageRenderElementType.JUNCTION_SPLIT &&
|
|
110
110
|
splitIdx > 0 &&
|
|
111
111
|
segmented) {
|
|
112
|
-
|
|
113
|
-
|
|
112
|
+
// Only hand later splits to a later host when that host also has junction
|
|
113
|
+
// (two-host diplomatic pattern). Seg-only follow-ons must not hide idx>0.
|
|
114
|
+
if (hasLaterJunctionHostInSegmentationGroup(elements, ref.uid, segmentationGroup, ref.p)) {
|
|
114
115
|
return true;
|
|
115
116
|
}
|
|
116
117
|
}
|
|
@@ -196,6 +197,30 @@ function getLastSegmentationPosInGroup(elements, start, end) {
|
|
|
196
197
|
}
|
|
197
198
|
return lastP;
|
|
198
199
|
}
|
|
200
|
+
function groupHasJunctionHost(elements, start, end) {
|
|
201
|
+
for (let i = start; i <= end; i += 1) {
|
|
202
|
+
const ref = elements[i].token;
|
|
203
|
+
if (ref && hasJunctionFromRef(ref)) {
|
|
204
|
+
return true;
|
|
205
|
+
}
|
|
206
|
+
}
|
|
207
|
+
return false;
|
|
208
|
+
}
|
|
209
|
+
function hasLaterJunctionHostInSegmentationGroup(elements, uid, groupKey, currentP) {
|
|
210
|
+
for (const element of elements) {
|
|
211
|
+
if (!isJunctionEditionElement(element))
|
|
212
|
+
continue;
|
|
213
|
+
const ref = element.token;
|
|
214
|
+
if (!sameSegmentationGroupRef(ref, uid, groupKey))
|
|
215
|
+
continue;
|
|
216
|
+
if (!hasSegmentationFromRef(ref))
|
|
217
|
+
continue;
|
|
218
|
+
if (ref.p > currentP) {
|
|
219
|
+
return true;
|
|
220
|
+
}
|
|
221
|
+
}
|
|
222
|
+
return false;
|
|
223
|
+
}
|
|
199
224
|
export function shouldSkipSegmentationElement(elements, index, selectedTier, corpus) {
|
|
200
225
|
if (!isUnderSelected(selectedTier, SEGMENTATION_TIER, corpus)) {
|
|
201
226
|
return false;
|
|
@@ -205,19 +230,99 @@ export function shouldSkipSegmentationElement(elements, index, selectedTier, cor
|
|
|
205
230
|
return false;
|
|
206
231
|
}
|
|
207
232
|
const { start, end } = findSegmentationGroupBounds(elements, index);
|
|
233
|
+
const ref = element.token;
|
|
234
|
+
// Junction host + seg-only pieces: diplomatic text lives on the junction host.
|
|
235
|
+
if (groupHasJunctionHost(elements, start, end)) {
|
|
236
|
+
if (hasJunctionFromRef(ref)) {
|
|
237
|
+
return false;
|
|
238
|
+
}
|
|
239
|
+
return true;
|
|
240
|
+
}
|
|
208
241
|
const lastP = getLastSegmentationPosInGroup(elements, start, end);
|
|
209
|
-
return
|
|
242
|
+
return ref.p < lastP;
|
|
210
243
|
}
|
|
211
244
|
/** @deprecated Use shouldSkipSegmentationElement */
|
|
212
245
|
export function shouldSkipSegmentationToken(elements, index, selectedTier, corpus) {
|
|
213
246
|
return shouldSkipSegmentationElement(elements, index, selectedTier, corpus);
|
|
214
247
|
}
|
|
248
|
+
function isMidJunctionHostLineBreak(elements, index) {
|
|
249
|
+
if (elements[index]?.type !== PageRenderElementType.LINE_BREAK) {
|
|
250
|
+
return false;
|
|
251
|
+
}
|
|
252
|
+
const prev = elements[index - 1];
|
|
253
|
+
if (prev?.type !== PageRenderElementType.JUNCTION_SPLIT || !prev.token) {
|
|
254
|
+
return false;
|
|
255
|
+
}
|
|
256
|
+
let nextIdx = index + 1;
|
|
257
|
+
while (nextIdx < elements.length &&
|
|
258
|
+
elements[nextIdx].type === PageRenderElementType.LINE_NUMBER) {
|
|
259
|
+
nextIdx += 1;
|
|
260
|
+
}
|
|
261
|
+
const next = elements[nextIdx];
|
|
262
|
+
if (next?.type !== PageRenderElementType.JUNCTION_SPLIT || !next.token) {
|
|
263
|
+
return false;
|
|
264
|
+
}
|
|
265
|
+
return prev.token.uid === next.token.uid && prev.token.p === next.token.p;
|
|
266
|
+
}
|
|
267
|
+
function sameDeferredBreakGroup(element, group) {
|
|
268
|
+
const ref = element.token;
|
|
269
|
+
if (!ref)
|
|
270
|
+
return false;
|
|
271
|
+
if (ref.uid === group.uid && ref.p === group.p)
|
|
272
|
+
return true;
|
|
273
|
+
if (group.segGroup &&
|
|
274
|
+
hasSegmentationFromRef(ref) &&
|
|
275
|
+
sameSegmentationGroupRef(ref, group.uid, group.segGroup)) {
|
|
276
|
+
return true;
|
|
277
|
+
}
|
|
278
|
+
return false;
|
|
279
|
+
}
|
|
215
280
|
export default function collapseElementsForTier(elements, selectedTier, corpus) {
|
|
216
281
|
const showJunctionSplits = isUnderSelected(selectedTier, JUNCTION_TIER, corpus);
|
|
217
282
|
const collapsed = [];
|
|
218
283
|
let index = 0;
|
|
284
|
+
let deferredBreak = null;
|
|
285
|
+
let deferredLineNumbers = [];
|
|
286
|
+
let deferredBreakGroup = null;
|
|
287
|
+
const flushDeferredBreak = () => {
|
|
288
|
+
if (!deferredBreak)
|
|
289
|
+
return;
|
|
290
|
+
collapsed.push({
|
|
291
|
+
kind: 'single',
|
|
292
|
+
element: deferredBreak,
|
|
293
|
+
key: `LINE_BREAK_deferred_${collapsed.length}`,
|
|
294
|
+
});
|
|
295
|
+
for (const lineNumber of deferredLineNumbers) {
|
|
296
|
+
collapsed.push({
|
|
297
|
+
kind: 'single',
|
|
298
|
+
element: lineNumber,
|
|
299
|
+
key: `LINE_NUMBER_deferred_${collapsed.length}`,
|
|
300
|
+
});
|
|
301
|
+
}
|
|
302
|
+
deferredBreak = null;
|
|
303
|
+
deferredLineNumbers = [];
|
|
304
|
+
deferredBreakGroup = null;
|
|
305
|
+
};
|
|
219
306
|
while (index < elements.length) {
|
|
220
307
|
const element = elements[index];
|
|
308
|
+
if (!showJunctionSplits &&
|
|
309
|
+
deferredBreak === null &&
|
|
310
|
+
isMidJunctionHostLineBreak(elements, index)) {
|
|
311
|
+
const host = elements[index - 1].token;
|
|
312
|
+
deferredBreak = element;
|
|
313
|
+
deferredBreakGroup = {
|
|
314
|
+
uid: host.uid,
|
|
315
|
+
p: host.p,
|
|
316
|
+
segGroup: segmentationGroupKey(host),
|
|
317
|
+
};
|
|
318
|
+
index += 1;
|
|
319
|
+
while (index < elements.length &&
|
|
320
|
+
elements[index].type === PageRenderElementType.LINE_NUMBER) {
|
|
321
|
+
deferredLineNumbers.push(elements[index]);
|
|
322
|
+
index += 1;
|
|
323
|
+
}
|
|
324
|
+
continue;
|
|
325
|
+
}
|
|
221
326
|
if (shouldSkipSegmentationElement(elements, index, selectedTier, corpus)) {
|
|
222
327
|
index += 1;
|
|
223
328
|
continue;
|
|
@@ -226,6 +331,12 @@ export default function collapseElementsForTier(elements, selectedTier, corpus)
|
|
|
226
331
|
index += 1;
|
|
227
332
|
continue;
|
|
228
333
|
}
|
|
334
|
+
const inDeferredGroup = !!element.token &&
|
|
335
|
+
!!deferredBreakGroup &&
|
|
336
|
+
sameDeferredBreakGroup(element, deferredBreakGroup);
|
|
337
|
+
if (deferredBreak && !inDeferredGroup) {
|
|
338
|
+
flushDeferredBreak();
|
|
339
|
+
}
|
|
229
340
|
if (!showJunctionSplits &&
|
|
230
341
|
element.type === PageRenderElementType.JUNCTION_SPLIT &&
|
|
231
342
|
element.token) {
|
|
@@ -251,6 +362,7 @@ export default function collapseElementsForTier(elements, selectedTier, corpus)
|
|
|
251
362
|
});
|
|
252
363
|
index += 1;
|
|
253
364
|
}
|
|
365
|
+
flushDeferredBreak();
|
|
254
366
|
return collapsed;
|
|
255
367
|
}
|
|
256
368
|
export function isTokenBearingCollapsed(item) {
|