DEV Community

John Peters
John Peters

Posted on • Updated on

Angular Form Controls and ngModels Don't mix

New Discovery
Use ngModel instead!

According to Angular, in discussing the ngModel and FormControls.

ngModel and FormControls Don't Mix

Use with ngModel is deprecated
Support for using the ngModel input property and ngModelChange event with reactive form directives has been deprecated in Angular v6 and is scheduled for removal in a future version of Angular.

Fallout
This means then, that use of Pipes (on HTML side) for an input element do not work any longer. Most content on StackOverflow shows tons of examples using the two together, don't do it.

But Why?
I don't know their internal architectural discussions but expect that the wave of immutable architecture took hold.

If we use Form Controls, we are being moved into the immutability pattern. The models that we once used for bindings are now replaced with the FormControl. The models themselves are to be set only twice in a particular workflow, once at start up time and then only once again when attempting to persist content for that control.

Mutable model architecture is on the outside of current Angular architectural trends.

What's the solution?
The pipe was a nice idea, it farmed off control for validation and formatting to another component. Indeed the FormControl overlapped some of that function. But if we are using Form Controls we have the ability to bypass Pipes.

FormControl Change Event Handlers

Assume an input element with SSN numbers, entered as string values, the model having a different value than the display. The model is just numeric when valid, while the display shows dashes in the numbers and or a string of hashes like this.

111
111-
111-22
111-22-3
111-22-3333

//or 

###-##-####

//model only winds up as
11122333
// or a semaphore such as 
0, -1, 999
Enter fullscreen mode Exit fullscreen mode

Replacing the Pipe

this.formGroup
  .controls.ssn.valueChanges
  .subscribe((value) => { 
     // do something with every change
     // no keyup event handlers needed 
}
Enter fullscreen mode Exit fullscreen mode

The event handler is responsible for validation and alteration of the data being displayed. The model, on the other hand is used for persisting the change and only when valid!

WorkFlow
-Initialize the FormControl with hash tags based on semaphore.

  • All FormControl changes do the same thing the pipe did, but are hooked to each change of the control.
  • The form control values are changed to format the SSN number as the values change until the end when all is valid, the model is updated.

Tip
Avoid Stack Overflow problems in the change event handler as follows:

if (newFormat === change) return;
this.formGroup
  .controls.ssn
  .setValue(newFormat);
Enter fullscreen mode Exit fullscreen mode

Our newFormat inserts the dashes as the user types. The problem is that each time we use setValue, we fire off another change! We have to stop the spiral-of-death and only set the newFormat once. If the newFormat is the same as the change, return!

Top comments (0)