javascript élément Knockoutjs-liaison à double sens perdue pour sélectionner la valeur lors de l'utilisation de foreach au lieu des options



sélection élément jquery (1)

J'ai deux contrôles sélectionnés.

L'un dépend de l'autre. Pour un exemple simple, supposons que le premier affiche une liste de villes, tandis que l'autre affiche une liste de rues dans chaque ville.

Lorsque la page est chargée initialement, le contrôle de sélection affichant les rues affiche toutes les rues disponibles. Cependant, une fois que l'utilisateur a choisi une ville dans la première sélection, la seconde sélection est filtrée pour afficher uniquement les rues appartenant à la ville sélectionnée.

Cela fonctionne bien lorsque vous utilisez la liaison d'options, cependant, j'ai besoin de la capacité de générer des optgroups et la liaison d'options ne le supporte pas, donc je dois utiliser la liaison foreach.

Le résultat est que chaque fois qu'une ville est sélectionnée, deux conséquences imprévues se produisent:

  1. La deuxième sélection (la liste filtrée des rues) semble avoir la première rue de la ville sélectionnée, même si j'utilise valueAllowUnset: true. Ceci n'est pas reflété dans le modèle de vue
  2. Lorsque vous sélectionnez réellement une rue dans la seconde, puis sélectionnez une autre ville dans la première sélection, la deuxième sélection se met à jour correctement pour refléter les modifications de la liste, mais pas le modèle de vue, conservant ainsi la valeur précédemment sélectionnée (même si ce n'est plus dans la liste). Même si je supprime valueAllowUnset: true à partir de la deuxième sélection, le problème persiste.

Y a-t-il une solution à ce problème? Je dois vraiment utiliser la liaison foreach au lieu de la liaison d'options.

JSFiddle: https://jsfiddle.net/jfxovLna/13/

var ViewModel = function() {

var self = this;

var regionAndCityArray = [{
 regionName: "Europe",
 cities: [{
   cityName: "London",
   additionalUnimportantInformation: 100
 }, {
   cityName: "Paris",
   additionalUnimportantInformation: 200
 }]
}, {
 regionName: "North America",
 cities: [{
   cityName: "New York",
   additionalUnimportantInformation: 45
 }]
}];

var cityAndStreetArray = [{
 cityName: "London",
 streets: [{
   streetName: "Parker",
   streetLength: 5
 }, {
   streetName: "Macklin",
   streetLength: 10
 }, ]
}, {
  cityName: "New York",
 streets: [{
   streetName: "5th Avenue",
   streetLength: 3
 }, {
   streetName: "Park Ave",
   streetLength: 12
 }]
}, {
  cityName: "Paris",
 streets: [{
   streetName: "Rue de Turbigo",
   streetLength: 11
 }, {
   streetName: "Rue aux Ours",
   streetLength: 12
 }]
}];

var getAvailableStreets = function() {

 var availableStreets = cityAndStreetArray;

 var selectedCity = self.selectedCity();

 var selectedRegion = _.find(regionAndCityArray,
   function(region) {
     return _.find(region.cities,
       function(city) {
         return city.cityName === selectedCity;
       });
   });

 if (selectedRegion == undefined) {
   return availableStreets;
 }

 var filteredStreets = _.filter(cityAndStreetArray,
   function(city) {
     return city.cityName === selectedCity;
   });

 return filteredStreets;
}

self.availableCities = ko.observableArray(regionAndCityArray);
self.selectedCity = ko.observable();
self.availbleStreets = ko.computed(getAvailableStreets);
self.selectedStreet = ko.observable();

};
var viewModel = new ViewModel();
ko.applyBindings(viewModel);

D'abord, ajoutez une option vide à votre entrée de sélection.

<option value="">Select Street</option>

Abonnez-vous maintenant à la propriété SelectedCity de votre modèle de vue. Chaque fois que cela change, configurez la rue sélectionnée par ''.

viewModel.selectedCity.subscribe(function() { 
  viewModel.selectedStreet(''); 
}, viewModel); 

De cette façon, vous pouvez résoudre vos deux problèmes.

Fait les changements dans ton violon et ça marche. essaie de le mettre à jour.

Voici un violon - https://jsfiddle.net/Shabi_669/w1vcjbjo/





viewmodel