fix(web): another simplification

Plus another unit test.

Test-bot: skip
This commit is contained in:
Eberhard Beilharz 2025-11-28 12:03:11 +01:00
parent e442fc36d6
commit bf652fb18c
No known key found for this signature in database
GPG key ID: E9140597606020D3
2 changed files with 44 additions and 18 deletions

View file

@ -177,32 +177,26 @@ export class CoreKeyboardProcessor extends EventEmitter<EventMap> implements Key
const deadkeyIterator = deadkeys.values();
let deadkey = deadkeyIterator.next();
const textMax = Math.min(text.length, caretPosition + 1);
let textIndex = 0;
while (!deadkey.done || textIndex < textMax) {
// insert 0 or more deadkeys at current index
while (!deadkey.done && deadkey.value.p <= textIndex) {
if (deadkey.value.p < textIndex) {
// this should never happen -- it would mean that
// a deadkey position was < 0 or in the middle of a
// surrogate pair. We'll silently drop it
console.warn(`invalid deadkey '${deadkey.value.d}' position ${deadkey.value.p}`);
} else {
const contextItem = new KM_Core.instance.km_core_context_item();
contextItem.marker = deadkey.value.d;
contextItems.push_back(contextItem);
}
while (!deadkey.done || textIndex < text.length) {
// flush out invalid deadkeys
while (!deadkey.done && (deadkey.value.p < textIndex || deadkey.value.p > text.length)) {
// this should never happen -- it would mean that a deadkey position was < 0, in the
// middle of a surrogate pair, or after the caret.
console.warn(`invalid deadkey '${deadkey.value.d}' position ${deadkey.value.p}`);
deadkey = deadkeyIterator.next();
}
// flush out invalid deadkeys
while (!deadkey.done && deadkey.value.p > textMax) {
console.warn(`invalid deadkey '${deadkey.value.d}' position ${deadkey.value.p} after end of text ${textMax}`);
// insert 0 or more deadkeys at current index
while (!deadkey.done && deadkey.value.p == textIndex) {
const contextItem = new KM_Core.instance.km_core_context_item();
contextItem.marker = deadkey.value.d;
contextItems.push_back(contextItem);
deadkey = deadkeyIterator.next();
}
// insert next character
if (textIndex < textMax) {
if (textIndex < text.length) {
const contextItem = new KM_Core.instance.km_core_context_item();
contextItem.character = text.codePointAt(textIndex);
contextItems.push_back(contextItem);

View file

@ -454,5 +454,37 @@ describe('CoreKeyboardProcessor', function () {
assert.equal(items.get(2).type, KM_CORE_CT.END, 'Item 2 should be END');
result.delete();
});
it('skips invalid deadkeys', function () {
// Setup
textStore = new SyntheticTextStore('abcde', 3);
textStore.deadkeys().add(new Deadkey(-1, 1)); // invalid
textStore.deadkeys().add(new Deadkey(1, 2)); // after 'b'
textStore.deadkeys().add(new Deadkey(4, 3)); // invalid (after caret)
// Execute
coreProcessor.unitTestEndPoints.applyContextFromTextStore(context, textStore);
// Verify
const result = KM_Core.instance.context_get(context);
assert.equal(result.status, KM_CORE_STATUS.OK);
const items = result.object;
// Text index : 0 1 1 2 3
// Text: : |
// context index: 0 1 2 3 4
// ContextItems : a dk2 b c END
assert.equal(items.size(), 5, 'Should have 5 context items');
assert.equal(items.get(0).type, KM_CORE_CT.CHAR, 'Item 0 should be CHAR');
assert.equal(items.get(0).character, 'a'.charCodeAt(0), 'Item 0 should be "a"');
assert.equal(items.get(1).type, KM_CORE_CT.MARKER, 'Item 1 should be MARKER');
assert.equal(items.get(1).marker, 2, 'Item 1 should be marker 2');
assert.equal(items.get(2).type, KM_CORE_CT.CHAR, 'Item 2 should be CHAR');
assert.equal(items.get(2).character, 'b'.charCodeAt(0), 'Item 2 should be "b"');
assert.equal(items.get(3).type, KM_CORE_CT.CHAR, 'Item 3 should be CHAR');
assert.equal(items.get(3).character, 'c'.charCodeAt(0), 'Item 3 should be "c"');
assert.equal(items.get(4).type, KM_CORE_CT.END, 'Item 4 should be END');
result.delete();
});
});
});