setSelectionRange function
Custom implementation to prevent the error that TextInputElementBase.setSelectionRange throws when called on an EmailInputElement or NumberInputElement since ONLY Chrome does not support it.
A warning will be displayed in the console instead of an error.
Example that will throw an exception in Chrome: InputElement inputNodeRef;
// This will throw an exception in Chrome when the node is focused.
renderEmailInput() {
return (Dom.input()
..type = 'email'
..onFocus = (_) {
inputNodeRef.setSelectionRange(inputNodeRef.value.length, inputNodeRef.value.length);
}
..ref = (instance) { inputNodeRef = instance; }
)();
}
Example that will not throw: InputElement inputNodeRef;
// This will not throw an exception - and will work in all
// browsers except Chrome until
// https://bugs.chromium.org/p/chromium/issues/detail?id=324360
// is fixed.
renderChromeSafeEmailInput() {
return (Dom.input()
..type = 'email'
..onFocus = (_) {
setSelectionRange(inputNodeRef, inputNodeRef.value.length, inputNodeRef.value.length);
}
..ref = (instance) { inputNodeRef = instance; }
)();
}
Implementation
void setSelectionRange(/* TextInputElement | TextAreaElement */Element? input, int start, int end, [String? direction]) {
if (input is TextAreaElement) {
input.setSelectionRange(start, end, direction);
} else if (input is InputElement && supportsSelectionRange(input)) {
if (browser.isChrome || browser.isFirefox) {
final inputType = input.getAttribute('type');
if (inputType == 'email' || inputType == 'number') {
assert(ValidationUtil.warn(unindent(
'''
Google Chrome does not support `setSelectionRange` on email or number inputs.
See: https://bugs.chromium.org/p/chromium/issues/detail?id=324360
'''
), input));
return;
}
}
input.setSelectionRange(start, end, direction);
} else {
throw ArgumentError.value(input, 'input', 'must be an instance of `TextInputElementBase`, `NumberInputElement` or `TextAreaElement`');
}
}