2

This is more of an approach based question rather than a coding question. I have to create a form with 3 fields i.e Name, Description, and text

this is what my mod.ts looks like.

mod.ts

export interface Mod {
  id: number,
    name ? : string,
    clauseList: Clause
}

export interface Clause {
  cName ? : string,
    cid ? : number,
    description: string,
    id ? : number,
    text ? : Text
}


export interface Text {
  cid: number
  txt ? : string,
    tid ? : number

}

as shown

My first question is should I go for template-driven forms or reactive forms for this project?

One of the requirements from the 3rd field is that every time the user hits enter, the tid should increment by 1 and whatever the user enters should be saved as a different formgroup. cid should be that of Clause object. for example :

txt = "hi",
tid =1,
cid = 1 

after pressing enter

txt = "welcome to our shop",
tid = 2,
cid = same as above

Can anyone help me with this? For a better reference I will post another of my questions which kinda uses the same format, It might help you figure out this question better TypeScript for loop in a nested Array?

My contact lenses have dried up, I have been staring for too long at my screen. Please ask me for more clarification. May the force be with you.

shrys
  • 5,860
  • 2
  • 21
  • 36
MenimE
  • 274
  • 6
  • 18
  • Opinion-based/recommendation questions are [off-topic](https://stackoverflow.com/help/on-topic) on Stack Overflow, and you can see why in the answers here - multiple people arguing in favor of both, with no way for a visitor to know which side is correct. – John Montgomery Dec 12 '19 at 22:47
  • Duplicate of https://stackoverflow.com/questions/39142616/what-are-the-practical-differences-between-template-driven-and-reactive-forms – Oleksandr Vetoshkin Dec 13 '19 at 12:16
  • @OleksandrVetoshkin I don't think it is a duplicate, I have asked people to assist me with a specific issue, along with asking which approach should I implement – MenimE Dec 14 '19 at 06:53

5 Answers5

3

Use Reactive Form

Reasons:- Easy to create dynamic formGroup dynamic form

  • Entire control of the form is in your hands.
  • Highly unit testable
siddharth shah
  • 1,139
  • 1
  • 9
  • 17
1

It depends on the requirement you have. Lets say if you have to create some Login/Registration form, validation comes into picture and showing inline validation error messages considered as good user experience instead of in some Toastr. For such cases 'Reactive Forms' are used. For simple forms or just to collect some sort of data you can go with Template driven forms.

To hold values on every key Enter:

HTML:

TS:

public formVal = [];
txt = '';
name = '';
desc = '';

onEnter(event) {
    if (event && event.keyCode === 13) {
        const obj = {
            name: this.name,
            desc: this.desc,
            txt: this.txt
        };
        formVal.push(obj);
    }
}
Sucharitha Suchi
  • 328
  • 3
  • 12
  • Validation is still easier in template forms, there is no use case that can't be solved with template forms. – Adrian Brand Dec 12 '19 at 06:15
  • I do not require validation in my form, all that worries me is the functionality of the 3rd field. I have no clue about how to make that. – MenimE Dec 12 '19 at 08:13
  • 1
    @MenimE, you can maintain a global array to push the required values in object format. write keypress event, in this event check for 'event.keyCode === '13' which is 'enter' button keycode. if it matches then push the object into array.So that you will be having all the values holded in this array – Sucharitha Suchi Dec 12 '19 at 08:30
  • So here is what i "fetch" from your comment, I create an input field using Reactive Form, look for an event and push the data into an array? – MenimE Dec 12 '19 at 12:36
  • yes.. you can either use Reactive form and push that form object or you can give ngModel to all the fields and access those values in TS file and frame object then push as updated above in answer. txt = ''; name = ''; desc = ''; are ts variables and in html you can use these variable for ngModel like ' – Sucharitha Suchi Dec 13 '19 at 06:07
  • After a long discussion, I was told to use Template-Driven form. Anyways, if you could take a look at this demo and me with my POST request [link](https://stackoverflow.com/questions/59337919/post-data-from-two-forms-as-one-object-in-angular/59338075#59338075) – MenimE Dec 15 '19 at 04:55
0

Use Template Forms

Much easier to learn and maintain.

No double handling of data, just bind your model to your template instead of having to create form objects and bind them to your template.

Easy to create reusable validation attributes, a little bit more boiler plate that reactive validators but the same functions.

Highly unit testable and you are testing the actual template bindings, not just an object that might be incorrectly bound in your template. You just need to awaits a component update which can be easily abstracted away into a helper function.

Adrian Brand
  • 20,384
  • 4
  • 39
  • 60
  • With Reactive forms you can manipulate form from the TS file itself, which is much more convenient than template driven forms – siddharth shah Dec 12 '19 at 05:54
  • My third field for entering the details as a paragraph is confusing me the most. I know I can dynamically add fields but according to the requirement it should be one textbox (like this comment tb) and everytime i press enter a new hidden input field should be created automatically. Like one of them "please enter your skills separated by Enter or in different lines" inputs. Can we do that using Template-driven forms? If yes, would you please share something that can help me? – MenimE Dec 12 '19 at 08:11
  • The key to template forms is every form field needs a unique name so you need something like [name]="'description_' + i" where i is the index. Do up a StackBlitz and I can help you get it working. – Adrian Brand Dec 12 '19 at 08:29
  • Here is something I need help with now. You can, also, show me how to add a paragraph in an input field. Here is the [link](https://stackoverflow.com/questions/59337919/post-data-from-two-forms-as-one-object-in-angular/59338075#59338075) – MenimE Dec 15 '19 at 04:54
0

Reactive Forms provides a rich API for managing forms of any complexity, it's highly testable and maintainable, it allows you to easily create dynamic forms and apply complex validation, so it's suitable for almost every form. Template Forms are suitable for only some simple things when you need just to bind some input without any validation, for example, the search field.

  • There is no complexity that reactive forms can achieve that template forms cannot. In AngularJs we did not have reactive forms and in Angular template forms are better. – Adrian Brand Dec 12 '19 at 22:44
  • @AdrianBrand, template-driven forms are harder to read, test and maintain, it's a legacy solution, there are no benefits of using template forms. – Oleksandr Vetoshkin Dec 13 '19 at 08:59
  • That is just not true! – Adrian Brand Dec 13 '19 at 10:53
  • @AdrianBrand, why are you thinking so? – Oleksandr Vetoshkin Dec 13 '19 at 12:15
  • Template form require double handling, you need to build the form object and then bind the form object to your template. There is more boiler plate in building validators but once you have a library of them they are super easy to apply. They are easier for junior devs to learn and easier to maintain. Testing is a bit harder as they are async but I have built test helpers that make it really easy to write test that are not just testing the form but also the template bindings. – Adrian Brand Dec 15 '19 at 06:17
  • My job is to make patterns for one of Australia's largest government departments and we have an army of devs that range from green monkey STEM graduates to expensive contractors. Take a look at these stack blitz https://stackblitz.com/edit/angular-pytks5 and https://stackblitz.com/edit/angular-t1wshi. There is no code, these are fully validated forms that have all the aria tags required for government compliance and my green monkeys can knock these out all day long. – Adrian Brand Dec 15 '19 at 06:21
  • And then look at one of the spec files https://github.com/adriandavidbrand/ngx-ez/blob/master/projects/ngx-ez-demo/src/app/app.component.spec.ts to see how we can actually test the template bindings and validation in a 4 line spec. You can do all this in reactive forms but it would cost way more and my army of green monkeys would be no where near as productive. – Adrian Brand Dec 15 '19 at 06:23
0

Here is an actual answer to the question rather than just template forms vs reactive forms. I am using template forms in this answer.

https://stackblitz.com/edit/angular-bmcapk

Have an array of your mods

mods = [{ id: 0 }]; // This is a simplified model for mod, but demonstrates the principal.

and in the template

<ng-container *ngFor="let mod of mods">
  <label>
    Name<input [name]="'name_' + mod.id" [(ngModel)]="mod.name" autoFocus>
  </label><br>
  <label>
    Desc
    <input [name]="'description_' + mod.id" [(ngModel)]="mod.description">
  </label><br>
  <textarea [name]="'text_' + mod.id" [(ngModel)]="mod.text" (keydown)="checkKey($event)"></textarea><br>
</ng-container>

Iterate over the array of mods and bind each mod to your form, use the id to create a unique name for each form field.

checkKey(e) {
  if (e.keyCode === 13) {
    this.mods.push({ id: this.mods[this.mods.length - 1].id + 1 });
    e.preventDefault();
  }
}

In the text field I have a keydown check to see if enter has been pressed. If it has add another mod to the array with an incremented id and prevent default to stop a new line being added to the textbox.

There is also a directive called autoFocus on the name so that when it first appears focus is taken from the text and put on the newly created mod's name.

@Directive({
    selector: '[autoFocus]'
})
export class AutofocusDirective {
  public constructor(private el: ElementRef) {
    setTimeout(() => { el.nativeElement.focus(); });
  }
}
Adrian Brand
  • 20,384
  • 4
  • 39
  • 60