forms - form - Angular2-Enlace de botón de radio
ng disabled angular 4 (14)
Aquí está la mejor manera de usar botones de radio en Angular2. No es necesario usar el evento (clic) o un RadioControlValueAccessor para cambiar el valor de la propiedad enlazada, establecer la propiedad [marcada] hace el truco.
<input name="options" type="radio" [(ngModel)]="model.options" [value]="1"
[checked]="model.options==1" /><br/>
<input name="options" type="radio" [(ngModel)]="model.options" [value]="2"
[checked]="model.options==2" /><br/>
Publiqué un ejemplo de uso de botones de radio: Angular 2: ¿cómo crear botones de radio desde la enumeración y agregar un enlace bidireccional? Funciona desde al menos Angular 2 RC5.
Quiero usar el botón de radio en un formulario usando Angular 2
Options : <br/>
1 : <input name="options" ng-control="options" type="radio" value="1" [(ng-model)]="model.options" ><br/>
2 : <input name="options" ng-control="options" type="radio" value="2" [(ng-model)]="model.options" ><br/>
El valor inicial de model.options es 1
cuando se carga la página, el primer botón de opción no está marcado y las modificaciones no están vinculadas al modelo
Alguna idea ?
Aquí hay una solución que me funciona. Involucra el enlace del botón de radio, pero no el enlace a los datos comerciales, sino el enlace al estado del botón de radio. Probablemente NO sea la mejor solución para nuevos proyectos, pero es apropiado para mi proyecto. Mi proyecto tiene un montón de código existente escrito en una tecnología diferente que estoy transfiriendo a Angular. El código anterior sigue un patrón en el que el código está muy interesado en examinar cada botón de opción para ver si es el seleccionado. La solución es una variación de las soluciones de controlador de clics, algunas de las cuales ya se han mencionado en . El valor agregado de esta solución puede ser:
- Funciona con el patrón de código antiguo con el que tengo que trabajar.
- Creé una clase auxiliar para tratar de reducir el número de declaraciones "if" en el controlador de clics y para manejar cualquier grupo de botones de opción.
Esta solución implica
- Usando un modelo diferente para cada botón de radio.
- Establecer el atributo "marcado" con el modelo del botón de opción.
- Pasar el modelo del botón de radio seleccionado a la clase auxiliar.
- La clase auxiliar se asegura de que los modelos estén actualizados.
- En el "tiempo de envío", esto permite que el código anterior examine el estado de los botones de radio para ver cuál se selecciona al examinar los modelos.
Ejemplo:
<input type="radio"
[checked]="femaleRadioButtonModel.selected"
(click)="radioButtonGroupList.selectButton(femaleRadioButtonModel)"
...
import {UIButtonControlModel} from "./ui-button-control.model";
export class UIRadioButtonGroupListModel {
private readonly buttonList : UIButtonControlModel[];
private readonly debugName : string;
constructor(buttonList : UIButtonControlModel[], debugName : string) {
this.buttonList = buttonList;
this.debugName = debugName;
if (this.buttonList == null) {
throw new Error("null buttonList");
}
if (this.buttonList.length < 2) {
throw new Error("buttonList has less than 2 elements")
}
}
public selectButton(buttonToSelect : UIButtonControlModel) : void {
let foundButton : boolean = false;
for(let i = 0; i < this.buttonList.length; i++) {
let oneButton : UIButtonControlModel = this.buttonList[i];
if (oneButton === buttonToSelect) {
oneButton.selected = true;
foundButton = true;
} else {
oneButton.selected = false;
}
}
if (! foundButton) {
throw new Error("button not found in buttonList");
}
}
}
...
Cuando el usuario hace clic en un botón de opción, se invoca el método selectButton de la clase auxiliar. Se pasa el modelo para el botón de radio que se hizo clic. La clase auxiliar establece el campo booleano "seleccionado" del modelo pasado en verdadero y establece el campo "seleccionado" de todos los demás modelos de botón de radio en falso.
Durante la inicialización, el componente debe construir una instancia de la clase auxiliar con una lista de todos los modelos de botones de radio del grupo. En el ejemplo, "radioButtonGroupList" sería una instancia de la clase auxiliar cuyo código es:
<form name="form" (ngSubmit)="">
<div *ngFor="let item of options">
<input [(ngModel)]="model.option_id" type="radio" name="options" [value]="item.id"> {{ item.name }}
</div>
</form>
Estaba buscando el método correcto para manejar esos botones de radio aquí es un ejemplo de una solución que encontré aquí:
<tr *ngFor="let entry of entries">
<td>{{ entry.description }}</td>
<td>
<input type="radio" name="radiogroup"
[value]="entry.id"
(change)="onSelectionChange(entry)">
</td>
</tr>
Observe el onSelectionChange que pasa el elemento actual al método.
Este problema se resuelve en la versión Angular 2.0.0-rc.4, respectivamente, en formularios.
Incluya
"@angular/forms": "0.2.0"
en package.json.
Luego extiende tu bootstrap en main. Parte relevante:
...
import { AppComponent } from ''./app/app.component'';
import { disableDeprecatedForms, provideForms } from ''@angular/forms'';
bootstrap(AppComponent, [
disableDeprecatedForms(),
provideForms(),
appRouterProviders
]);
Tengo esto en .html y funciona perfectamente: valor: {{buildTool}}
<form action="">
<input type="radio" [(ngModel)]="buildTool" name="buildTool" value="gradle">Gradle <br>
<input type="radio" [(ngModel)]="buildTool" name="buildTool" value="maven">Maven
</form>
He creado una versión usando solo un evento de clic en los elementos cargados y pasando el valor de la selección a la función "getSelection" y actualizando el modelo.
En tu plantilla:
<ul>
<li *ngFor="let p of price"><input type="radio" name="price" (click)="getValue(price.value)" value="{{p}}" #price> {{p}}
</li>
</ul>
Tu clase:
export class App {
price:string;
price = ["1000", "2000", "3000"];
constructor() { }
model = new SomeData(this.price);
getValue(price){
this.model.price = price;
}
}
Ver ejemplo: https://plnkr.co/edit/2Muje8yvWZVL9OXqG0pW?p=info
La solución más simple y la solución alternativa:
<input name="toRent" type="radio" (click)="setToRentControl(false)">
<input name="toRent" type="radio" (click)="setToRentControl(true)">
setToRentControl(value){
this.vm.toRent.updateValue(value);
alert(value); //true/false
}
Lo siguiente solucionó mi problema, considere agregar una entrada de radio dentro de la etiqueta del
form
y use la etiqueta
[value]
para mostrar el valor.
<input type="radio"
[checked]="maleRadioButtonModel.selected"
(click)="radioButtonGroupList.selectButton(maleRadioButtonModel)"
Mi solución manual, que implica actualizar manualmente las
model.options
cuando se selecciona un nuevo botón de
model.options
:
template: `
<label *ngFor="let item of radioItems">
<input type="radio" name="options" (click)="model.options = item"
[checked]="item === model.options">
{{item}}
</label>`
class App {
radioItems = ''one two three''.split('' '');
model = { options: ''two'' };
}
Este Plunker demuestra lo anterior, así como también cómo usar un botón para cambiar el botón de radio seleccionado, es decir, para demostrar que el enlace de datos es bidireccional:
<button (click)="model.options = ''one''">set one</button>
Nota: el enlace del botón de radio ahora es una característica compatible en RC4 en adelante: consulte esta respuesta
Ejemplo de botón de radio usando RadioControlValueAccessor personalizado similar a CheckboxControlValueAccessor ( actualizado con Angular 2 rc-1 )
App.ts
import {Component} from "@angular/core";
import {FORM_DIRECTIVES} from "@angular/common";
import {RadioControlValueAccessor} from "./radio_value_accessor";
import {bootstrap} from ''@angular/platform-browser-dynamic'';
@Component({
selector: "my-app",
templateUrl: "template.html",
directives: [FORM_DIRECTIVES, RadioControlValueAccessor]
})
export class App {
model;
constructor() {
this.model = {
sex: "female"
};
}
}
template.html
<div>
<form action="">
<input type="radio" [(ngModel)]="model.sex" name="sex" value="male">Male<br>
<input type="radio" [(ngModel)]="model.sex" name="sex" value="female">Female
</form>
<input type="button" value="select male" (click)="model.sex=''male''">
<input type="button" value="select female" (click)="model.sex=''female''">
<div>Selected Radio: {{model.sex}}</div>
</div>
radio_value_accessor.ts
import {Directive, Renderer, ElementRef, forwardRef} from ''@angular/core'';
import {NG_VALUE_ACCESSOR, ControlValueAccessor} from ''@angular/common'';
export const RADIO_VALUE_ACCESSOR: any = {
provide: NG_VALUE_ACCESSOR,
useExisting: forwardRef(() => RadioControlValueAccessor),
multi: true
};
@Directive({
selector:
''input[type=radio][ngControl],input[type=radio][ngFormControl],input[type=radio][ngModel]'',
host: {''(change)'': ''onChange($event.target.value)'', ''(blur)'': ''onTouched()''},
bindings: [RADIO_VALUE_ACCESSOR]
})
export class RadioControlValueAccessor implements ControlValueAccessor {
onChange = (_) => {};
onTouched = () => {};
constructor(private _renderer: Renderer, private _elementRef: ElementRef) {}
writeValue(value: any): void {
this._renderer.setElementProperty(this._elementRef.nativeElement, ''checked'', value == this._elementRef.nativeElement.value);
}
registerOnChange(fn: (_: any) => {}): void { this.onChange = fn; }
registerOnTouched(fn: () => {}): void { this.onTouched = fn; }
}
Fuente: https://github.com/angular2-school/angular2-radio-button
Demostración en vivo de Plunker: http://plnkr.co/edit/aggee6An1iHfwsqGoE3q?p=preview
Por mucho que esta respuesta no sea la mejor según su caso de uso, funciona.
En lugar de usar el botón de radio para una selección masculina y femenina, usar
<select> </select>
funciona perfectamente, tanto para guardar como para editar.
<select formControlName="gender" name="gender" class="">
<option value="M">Male</option>
<option value="F">Female</option>
</select>
Lo anterior debería funcionar bien, para editar usando FormGroup con
patchValue
.
Para crear, puede usar
[(ngModel)]
lugar del
formControlName
.
Todavía funciona.
El trabajo de plomería involucrado con el botón de radio uno, elegí ir con el select en su lugar. Visualmente y en cuanto a UX, no parece ser el mejor, pero desde el punto de vista del desarrollador, es muchísimo más fácil.
Puede que esta no sea la solución correcta, pero esta también es una opción, espero que ayude a alguien.
Hasta ahora tenía el valor de radioButtons usando el método (clic) como el siguiente:
<input type="radio" name="options" #male (click)="onChange(male.value)">Male
<input type="radio" name="options" #female (click)="onChange(female.value)">Female
y en el archivo .ts he establecido el valor de la variable predefinida para obtener el valor de la función
onChange
.
Pero después de buscar, encontré un buen método que todavía no he probado, pero parece que este es bueno usando el enlace
[(ng-model)]
aquí para github
https://github.com/angular2-school/angular2-radio-button
.
esto está usando
RadioControlValueAccessor
para la radio, así como también la casilla de verificación.
Aquí está el # plnkr # de trabajo para este método
http://plnkr.co/edit/aggee6An1iHfwsqGoE3q?p=preview
.
[value] = "item" usando * ngFor también funciona con Formas reactivas en Angular 2 y 4
<label *ngFor="let item of items">
<input type="radio" formControlName="options" [value]="item">
{{item}}
</label>`
use [value] = "1" en lugar de value = "1"
<input name="options" ng-control="options" type="radio" [value]="1" [(ngModel)]="model.options" ><br/>
<input name="options" ng-control="options" type="radio" [value]="2" [(ngModel)]="model.options" ><br/>
Editar:
Como lo sugiere thllbrg "Para angular 2.1+ use
[(ngModel)]
lugar de
[(ng-model)]
"