После некоторой борьбы, я думаю, что вроде как разобрался ...
$('#input').on('input', onChange);
let before = '';
function onChange(target){
const { selectionStart: start, value: after } = target.currentTarget;
// calculate the different starting points from both direction
let p1 = 0, p2 = 0;
// calclate the end point first
for(; p2 < after.length - start; p2++){
if(before[before.length - 1 - p2] === undefined || before[before.length - 1 - p2] !== after[after.length - 1 - p2]){
break;
}
}
// calclate start point
for(; p1 < after.length - p2 - (after.length > before.length ? 1 : 0); p1++){
if(before[p1] !== after[p1] || p1 + p2 >= before.length){
break;
}
}
let insertedText = '';
let insertPosition = -1;
let deletedTextCount = 0;
let deletePosition = -1;
// has delete
if(p1 + p2 < before.length){
deletedTextCount = before.length - (p1 + p2);
deletePosition = p1;
}
// has add
if(p1 + p2 < after.length){
insertedText = after.substr(p1, after.length - (p1 + p2));
insertPosition = p1;
}
console.log(`deletePosition: ${deletePosition}, deletedTextCount: ${deletedTextCount}, insertPosition: ${insertPosition}, insertedText: "${insertedText}"`);
before = after;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<input id="input" type="text" />