Skip to content

Commit 94bf5e9

Browse files
mmalerbatinayuangao
authored andcommitted
fix(input): prevent input caret from sticking on iOS (#6128)
1 parent 3940fab commit 94bf5e9

File tree

1 file changed

+26
-12
lines changed

1 file changed

+26
-12
lines changed

src/lib/input/input-container.ts

Lines changed: 26 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -7,31 +7,31 @@
77
*/
88

99
import {
10-
AfterContentInit,
1110
AfterContentChecked,
11+
AfterContentInit,
1212
AfterViewInit,
13+
ChangeDetectionStrategy,
1314
ChangeDetectorRef,
1415
Component,
1516
ContentChild,
1617
ContentChildren,
1718
Directive,
19+
DoCheck,
1820
ElementRef,
21+
Inject,
1922
Input,
23+
OnChanges,
24+
OnDestroy,
2025
Optional,
2126
QueryList,
2227
Renderer2,
2328
Self,
2429
ViewChild,
2530
ViewEncapsulation,
26-
Inject,
27-
ChangeDetectionStrategy,
28-
OnChanges,
29-
OnDestroy,
30-
DoCheck,
3131
} from '@angular/core';
3232
import {animate, state, style, transition, trigger} from '@angular/animations';
3333
import {coerceBooleanProperty, Platform} from '../core';
34-
import {FormGroupDirective, NgControl, NgForm, FormControl} from '@angular/forms';
34+
import {FormControl, FormGroupDirective, NgControl, NgForm} from '@angular/forms';
3535
import {getSupportedInputTypes} from '../core/platform/features';
3636
import {
3737
getMdInputContainerDuplicatedHintError,
@@ -41,13 +41,13 @@ import {
4141
} from './input-container-errors';
4242
import {
4343
FloatPlaceholderType,
44-
PlaceholderOptions,
45-
MD_PLACEHOLDER_GLOBAL_OPTIONS
44+
MD_PLACEHOLDER_GLOBAL_OPTIONS,
45+
PlaceholderOptions
4646
} from '../core/placeholder/placeholder-options';
4747
import {
4848
defaultErrorStateMatcher,
49-
ErrorStateMatcher,
5049
ErrorOptions,
50+
ErrorStateMatcher,
5151
MD_ERROR_GLOBAL_OPTIONS
5252
} from '../core/error/error-options';
5353
import {Subject} from 'rxjs/Subject';
@@ -138,7 +138,6 @@ export class MdSuffix {}
138138
}
139139
})
140140
export class MdInputDirective implements OnChanges, OnDestroy, DoCheck {
141-
142141
/** Variables used as cache for getters and setters. */
143142
private _type = 'text';
144143
private _placeholder: string = '';
@@ -232,7 +231,6 @@ export class MdInputDirective implements OnChanges, OnDestroy, DoCheck {
232231
constructor(private _elementRef: ElementRef,
233232
private _renderer: Renderer2,
234233
private _platform: Platform,
235-
private _changeDetectorRef: ChangeDetectorRef,
236234
@Optional() @Self() public _ngControl: NgControl,
237235
@Optional() private _parentForm: NgForm,
238236
@Optional() private _parentFormGroup: FormGroupDirective,
@@ -242,6 +240,22 @@ export class MdInputDirective implements OnChanges, OnDestroy, DoCheck {
242240
this.id = this.id;
243241
this._errorOptions = errorOptions ? errorOptions : {};
244242
this.errorStateMatcher = this._errorOptions.errorStateMatcher || defaultErrorStateMatcher;
243+
244+
// On some versions of iOS the caret gets stuck in the wrong place when holding down the delete
245+
// key. In order to get around this we need to "jiggle" the caret loose. Since this bug only
246+
// exists on iOS, we only bother to install the listener on iOS.
247+
if (_platform.IOS) {
248+
_renderer.listen(_elementRef.nativeElement, 'keyup', (event: Event) => {
249+
let el = event.target as HTMLInputElement;
250+
if (!el.value && !el.selectionStart && !el.selectionEnd) {
251+
// Note: Just setting `0, 0` doesn't fix the issue. Setting `1, 1` fixes it for the first
252+
// time that you type text and then hold delete. Toggling to `1, 1` and then back to
253+
// `0, 0` seems to completely fix it.
254+
el.setSelectionRange(1, 1);
255+
el.setSelectionRange(0, 0);
256+
}
257+
});
258+
}
245259
}
246260

247261
ngOnChanges() {

0 commit comments

Comments
 (0)