एंगुलर में ऑब्जेक्ट को चुनने के लिए बाइंडिंग एलिमेंट


409

मैं एक चयनित तत्व को वस्तुओं की सूची में बाँधना चाहता हूँ - जो कि काफी आसान है:

@Component({
   selector: 'myApp',
   template: `<h1>My Application</h1>
              <select [(ngModel)]="selectedValue">
                 <option *ngFor="#c of countries" value="c.id">{{c.name}}</option>
              </select>`
})
export class AppComponent{
    countries = [
       {id: 1, name: "United States"},
       {id: 2, name: "Australia"}
       {id: 3, name: "Canada"},
       {id: 4, name: "Brazil"},
       {id: 5, name: "England"}
     ];
    selectedValue = null;
}

इस मामले में, ऐसा प्रतीत होता है कि selectedValueएक संख्या होगी - चयनित आइटम की आईडी।

हालाँकि, मैं वास्तव में देश के ऑब्जेक्ट के लिए बाध्य करना चाहूंगा ताकि selectedValueकेवल आईडी के बजाय ऑब्जेक्ट हो। मैंने विकल्प के मूल्य को बदलने की कोशिश की जैसे:

<option *ngFor="#c of countries" value="c">{{c.name}}</option>

लेकिन यह काम नहीं करता है। यह मेरे लिए एक वस्तु रखने के लिए लगता है selectedValue- लेकिन उस वस्तु को नहीं जो मैं उम्मीद कर रहा हूं। आप इसे मेरे प्लंकर उदाहरण में देख सकते हैं

मैंने भी परिवर्तन की घटना के लिए बाध्य करने की कोशिश की ताकि मैं चयनित आईडी के आधार पर वस्तु को स्वयं निर्धारित कर सकूं; हालाँकि, ऐसा प्रतीत होता है कि बाउंड एनकोडेल के अपडेट होने से पहले परिवर्तन की घटना समाप्त हो जाती है - मतलब उस बिंदु पर मेरे पास नए चयनित मूल्य तक पहुंच नहीं है।

क्या एंगुलर 2 के साथ किसी चयनित तत्व को बांधने का एक साफ तरीका है?


बस एहसास हुआ कि मेरा प्लंक IE बनाम क्रोम में थोड़ा अलग तरीके से काम करता है। न तो कोई वास्तव में मेरे इच्छित तरीके से काम करता है, लेकिन FYI करें।
RHarris

जवाबों:


733
<h1>My Application</h1>
<select [(ngModel)]="selectedValue">
  <option *ngFor="let c of countries" [ngValue]="c">{{c.name}}</option>
</select>

StackBlitz उदाहरण

नोट: यदि आप उपयोग कर सकते हैं [ngValue]="c"के बजाय [ngValue]="c.id"जहां ग पूरा देश वस्तु है।

[value]="..."केवल स्ट्रिंग मान
[ngValue]="..."का समर्थन करता है किसी भी प्रकार का समर्थन करता है

अपडेट करें

यदि valueएक वस्तु है, तो preselected उदाहरण को मूल्यों में से एक के साथ समान होना चाहिए।

4.0.0-beta.7 के बाद से उपलब्ध हाल ही की गयी कस्टम तुलना https://github.com/angular/angular/issues/13268 भी देखें

<select [compareWith]="compareFn" ...

अगर आप thisभीतर पहुंचना चाहते हैं तो ध्यान रखें compareFn

compareFn = this._compareFn.bind(this);

// or 
// compareFn = (a, b) => this._compareFn(a, b);

_compareFn(a, b) {
   // Handle compare logic (eg check if unique ids are the same)
   return a.id === b.id;
}

21
कोशिश की, लेकिन यह केवल ड्रॉपडाउन से मॉडल के लिए डेटा-बाइंड लगता है। यदि मॉडल के साथ पृष्ठ में प्रवेश करने से पहले से ही ड्रॉपडाउन सेट हो जाता है तो उसके अनुसार सेट नहीं किया जाता ...
Strinder

13
@Strinder के लिए एक अन्य गलती उदाहरण के लिए (डिफ़ॉल्ट आइटम) की selectedValueतुलना में किसी अन्य ऑब्जेक्ट का उपयोग करना है c। समान गुणों और मूल्यों के साथ भी एक अलग वस्तु काम नहीं करती है, यह एक ही वस्तु उदाहरण होना चाहिए।
गुंटर ज़ोचबॉयर

1
@ गुंटरेज़ोचबॉएर हाँ। पहले से ही सोचा था। तो मॉडल और मूल्यों की सूची के साथ सीधे सिंक करने का कोई आसान तरीका नहीं है? हमेशा onChange के माध्यम से?

1
जल्द ही हम कस्टम तुलनित्र फ़ंक्शन का उपयोग करते हुए उनकी संपत्ति द्वारा ngModel ऑब्जेक्ट्स की तुलना करने में सक्षम हो सकते हैं। जरा इस मुद्दे को देखें: github.com/angular/angular/issues/13268
kub1x

1
यह हमेशा आसान एक बार आप इसे पता है ;-) लेकिन angular.io/api/forms/NgSelectOption#description एक लिंक होता है angular.io/api/forms/SelectControlValueAccessor अच्छा डॉक्स के साथ।
गुंटर ज़ोचबॉयर

41

यह मदद कर सकता है:

    <select [(ngModel)]="selectedValue">
          <option *ngFor="#c of countries" [value]="c.id">{{c.name}}</option>
    </select>

5
मैंने [ngValue] के बजाय [value] का उपयोग किया है। यह वैसा नहीं है। यह मेरे लिए काम किया
कैरोलिना फाएडो

2
कोणीय 4 में '#' पर त्रुटि
समुद्री-किलो

2
@ समुद्र-किलो के letबजाय का उपयोग करें#
अशराफुल इस्लाम

1
इस उत्तर को चयनित मान नहीं मिलता है
सैन जैसी

20

आप [(ngModel)]अपने <select>टैग में उपयोग करने की आवश्यकता के बिना भी ऐसा कर सकते हैं

अपनी ts फ़ाइल में एक वैरिएबल घोषित करें

toStr = JSON.stringify;

और आप टेम्पलेट में ऐसा करते हैं

 <option *ngFor="let v of values;" [value]="toStr(v)">
      {{v}}
 </option>

और फिर उपयोग करें

let value=JSON.parse(event.target.value)

स्ट्रिंग को एक मान्य जावास्क्रिप्ट ऑब्जेक्ट में वापस पार्स करने के लिए


1
यह वास्तव में उल्लेखनीय है, लेकिन बड़ी वस्तुओं पर एक दर्द बन जाएगा। इसके अलावा, परिवर्तन का पता लगाने की एंगुलर की अंडरलाइन क्षमता के बारे में सोचा जाना चाहिए। बॉट्स द्वारा आसानी से पार्स करने योग्य जानकारी को जुसन के रूप में आउटपुट किया जाता है। कोणीय परिवर्तन का पता लगाने का उपयोग डेटा के तर्क को छुपाता है (एनकैप्सुलेट करता है), और आपको आपकी आवश्यक जानकारी का आश्वासन देता है। @ गुंटर ज़ोचबॉयर उत्तर कोणीय में करने का तरीका है। :)
लुकासी आंद्रेई

मेरी मदद की जहां मेरी एक सूची थी और एक मान को बदलने के लिए अगले को अपडेट नहीं करना चाहिए, इसलिए इसे ngmodel के उपयोग के बिना हैक के रूप में उपयोग करने में मदद मिली, धन्यवाद :)
मेल्विन

यह सादे जावास्क्रिप्ट ऑब्जेक्ट्स के लिए काम करता है लेकिन एक वर्ग के उदाहरणों के लिए ध्यान दें कि आप इस पर सभी तरीकों को खो देंगे।
खलीलरावण

13

इसने मेरे लिए काम किया:

टेम्पलेट HTML:

मैंने (ngModelChange)="selectChange($event)"अपने को जोड़ा select

<div>
  <label for="myListOptions">My List Options</label>
  <select (ngModelChange)="selectChange($event)" [(ngModel)]=model.myListOptions.id >
    <option *ngFor="let oneOption of listOptions" [ngValue]="oneOption.id">{{oneOption.name}}</option>
  </select>
</div>

कंपोनेंट पर:

  listOptions = [
    { id: 0, name: "Perfect" },
    { id: 1, name: "Low" },
    { id: 2, name: "Minor" },
    { id: 3, name: "High" },
  ];

आपको component.tsइस फ़ंक्शन में जोड़ने की आवश्यकता है :

  selectChange( $event) {
    //In my case $event come with a id value
    this.model.myListOptions = this.listOptions[$event];
  }

नोट: मैं कोशिश करता हूं [select]="oneOption.id==model.myListOptions.id"कि काम न करूं ।

============= अन्य तरीके हो सकते हैं: =========

टेम्पलेट HTML:

मैंने [compareWith]="compareByOptionIdअपने को जोड़ा select

<div>
  <label for="myListOptions">My List Options</label>
  <select [(ngModel)]=model.myListOptions [compareWith]="compareByOptionId">
    <option *ngFor="let oneOption of listOptions" [ngValue]="oneOption">{{oneOption.name}}</option>
  </select>
</div>

कंपोनेंट पर:

  listOptions = [
    { id: 0, name: "Perfect" },
    { id: 1, name: "Low" },
    { id: 2, name: "Minor" },
    { id: 3, name: "High" },
  ];

आपको component.tsइस फ़ंक्शन में जोड़ने की आवश्यकता है :

 /* Return true or false if it is the selected */
 compareByOptionId(idFist, idSecond) {
    return idFist && idSecond && idFist.id == idSecond.id;
 }

यह अच्छा है अगर आप कुछ अतिरिक्त करने के लिए परिवर्तन घटना को संभालना चाहते हैं (जैसे कि कॉलबैक सूचित करें)। हालांकि उस मामले में, आपको केवल [ngModel]अपने मॉडल को अपने कस्टम परिवर्तन कॉलबैक में परिभाषित करने के लिए मैन्युअल रूप से रखना और फिर सेट करना होगा (ngModelChange)
क्रश

9

बस अगर कोई व्यक्ति प्रतिक्रियात्मक रूपों का उपयोग करके ऐसा करना चाहता है:

<form [formGroup]="form">
  <select formControlName="country">
    <option *ngFor="let country of countries" [ngValue]="country">{{country.name}}</option>
  </select>
  <p>Selected Country: {{country?.name}}</p>
</form>

यहां काम करने के उदाहरण की जाँच करें


5

आप एक फ़ंक्शन का उपयोग करके आईडी का चयन कर सकते हैं

<option *ngFor="#c of countries" (change)="onchange(c.id)">{{c.name}}</option>

4

मेरे लिए इस तरह से काम करना, आप सांत्वना दे सकते हैं event.target.value

<select (change) = "ChangeValue($event)" (ngModel)="opt">   
    <option *ngFor=" let opt of titleArr" [value]="opt"></option>
</select>

2

इसके अलावा, अगर दिए गए समाधानों के अलावा और कुछ भी काम नहीं करता है, तो जांचें कि क्या आपने "AppModule" के अंदर "FormModule" को आयात किया है, जो मेरे लिए एक कुंजी थी।


2

चयनित आइटम के लिए दूसरा गेट्टर बनाएं

<form [formGroup]="countryForm">
  <select formControlName="country">
    <option *ngFor="let c of countries" [value]="c.id">{{c.name}}</option>
  </select>

  <p>Selected Country: {{selectedCountry?.name}}</p>
</form>

Ts में:

get selectedCountry(){
  let countryId = this.countryForm.controls.country.value;
  let selected = this.countries.find(c=> c.id == countryId);
  return selected;
}

1

आप फ़ंक्शन के माध्यम से चयनित मूल्य को पारित करके क्लिक () की मदद से चयनित मूल्य भी प्राप्त कर सकते हैं

<md-select placeholder="Select Categorie"  
    name="Select Categorie" >
  <md-option *ngFor="let list of categ" [value]="list.value" (click)="sub_cat(list.category_id)" >
    {{ list.category }}
  </md-option>
</md-select>

0

इस तरह से भी उपयोग करें ।।

<h1>My Application</h1>
<select [(ngModel)]="selectedValue">
     <option *ngFor="let c of countries" value="{{c.id}}">{{c.name}}</option>
 </select>

0

इन app.component.html:

 <select type="number" [(ngModel)]="selectedLevel">
          <option *ngFor="let level of levels" [ngValue]="level">{{level.name}}</option>
        </select>

और app.component.ts:

import { Component } from '@angular/core';

@Component({
  selector: 'my-app',
  templateUrl: './app.component.html',
  styleUrls: [ './app.component.css' ]
})
export class AppComponent  {
  levelNum:number;
  levels:Array<Object> = [
      {num: 0, name: "AA"},
      {num: 1, name: "BB"}
  ];

  toNumber(){
    this.levelNum = +this.levelNum;
    console.log(this.levelNum);
  }

  selectedLevel = this.levels[0];

  selectedLevelCustomCompare = {num: 1, name: "BB"}

  compareFn(a, b) {
    console.log(a, b, a && b && a.num == b.num);
    return a && b && a.num == b.num;
  }
}

0

<select name="typeFather"
    [(ngModel)]="type.typeFather">
        <option *ngFor="let type of types" [ngValue]="type">{{type.title}}</option>
</select>

यह दृष्टिकोण हमेशा काम करने वाला है, हालांकि यदि आपके पास एक गतिशील सूची है, तो सुनिश्चित करें कि आप इसे मॉडल से पहले लोड करते हैं

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.