Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

FIX: Problem with cursor jumps and input behaviour for NumberInput #1945

Open
wants to merge 8 commits into
base: master
Choose a base branch
from

Conversation

divinedesign-se
Copy link

Fixes the jumping of input cursor in NumberInput when using keyboard backspace and delete to remove decimal values.

README.md Outdated Show resolved Hide resolved
src/NumberInput/NumberInput.svelte Outdated Show resolved Hide resolved
src/NumberInput/NumberInput.svelte Outdated Show resolved Hide resolved
src/NumberInput/NumberInput.svelte Outdated Show resolved Hide resolved
Comment on lines +158 to +188
const isIntegerTransition =
!data &&
!Number.isInteger(previousValue) &&
Number.isInteger(possibleNewValue);

if (isIntegerTransition && value < previousValue) {
await setSelectionAfterTick(target.value.length);
} else if (isIntegerTransition && previousValue && value > previousValue) {
let parts = previousValue.toString().split(".");

if (inputType === "deleteContentForward" && parts[1]) {
parts[1] = parts[1].substring(1);
} else if (inputType === "deleteContentBackward") {
parts[0] = parts[0].slice(0, -1);
}

const chars =
parts[0].length + (inputType === "deleteContentBackward" ? 1 : 0);
value = parse(parts.join("."));
await setSelectionAfterTick(chars);
} else if (
!isIntegerTransition &&
previousValue &&
value === previousValue &&
inputType === "deleteContentForward"
) {
value = parse(0);
await setSelectionAfterTick(0);
} else {
value = possibleNewValue;
}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This entire logic is hard to understand/follow, though I also don't know if/how it could be improved...

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The function starts by parsing the current value of the input field and storing it in previousValue. It then parses the new value of the input field and stores it in possibleNewValue and value.

Next, it checks if the input action resulted in a transition from a non-integer to an integer. This is determined by the isIntegerTransition variable, which is true if data is undefined, previousValue is not an integer, and possibleNewValue is an integer.

If isIntegerTransition is true and the new value is less than the previous value, it sets the cursor position to the end of the input field after the next tick.

If isIntegerTransition is true, the new value is greater than the previous value, and the previous value is not undefined, it splits the previous value into integer and fractional parts. Depending on the inputType, it removes a character from the fractional part or the integer part. It then joins the parts back together, parses the result, and sets it as the new value. It also sets the cursor position to a specific position after the next tick.

If isIntegerTransition is false, the new value is equal to the previous value, and the inputType is "deleteContentForward" (meaning the user pressed delete key instead of backspace), it sets the value to 0 and the cursor position to the start of the input field after the next tick.

If none of the above conditions are met, it simply sets the value to possibleNewValue.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants