Tableau observable dépendant dans Knockout JS

J’ai commencé à jouer avec knockoutjs et à faire une simple liaison / liaison dépendante. Mon objective est d’avoir une liste renseignée en fonction de la valeur d’une autre liste . Les deux sont en cours de chargement à partir d’un appel ajax vers mon service Web asp.net.

J’ai donc deux listes

   

Ensuite, mon javascript ressemble à ceci:

 $(function () { // creating the model var option = function (text, value) { this.text = text; this.value = value; } // creating the view model var searchModel = { availableMakes: ko.observableArray([]), availableModels: ko.observableArray([]), selectedMake: ko.observable(), selectedModel: ko.observable() } // adding in a dependentObservable to update the Models based on the selected Make searchModel.UpdateModels = ko.dependentObservable(function () { var theMake = searchModel.selectedMake() ? searchModel.selectedMake().text : ''; if (theMake != '') { $.ajax({ url: "/data/service/auction.asmx/GetModels", type: 'GET', contentType: "application/json; charset=utf-8", data: '{make:"' + theMake + '"}', success: function (data) { var makes = (typeof data.d) == 'ssortingng' ? eval('(' + data.d + ')') : data.d; var mappedModels = $.map(makes, function (item) { return new option(item.text, item.value); }); searchModel.availableModels(mappedModels); }, dataType: "json" }); } else { searchModel.availableModels([]); } return null; }, searchModel); // binding the view model ko.applyBindings(searchModel); // loading in all the makes $.ajax({ url: "/data/service/auction.asmx/GetMakes", type: 'GET', contentType: "application/json; charset=utf-8", data: '', success: function (data) { var makes = (typeof data.d) == 'ssortingng' ? eval('(' + data.d + ')') : data.d; var mappedMakes = $.map(makes, function (item) { return new option(item.text, item.value); }); searchModel.availableMakes(mappedMakes); }, dataType: "json" }); }); 

Actuellement, cela fonctionne comme prévu, mais je pense que je le fais mal car le code a l’air assez long, et je pourrais le faire sans utiliser knockoutjs dans moins de code. De plus, la façon dont je charge les availableModels n’est évidemment pas correcte, car j’utilise un object UpdateModels appelé UpdateModels que j’ai ajouté pour charger les availableModels fonction de la valeur de selectedMake().text

J’espère que cela a du sens et que vous pouvez indiquer une version améliorée de cela? Ou dites-moi simplement Comment recharger les modèles basés sur la sélection Make?

Merci beaucoup,

Je pense que votre code a l’air assez normal. Pour le DépendantObservable UpdateModels , vous pouvez utiliser un abonnement manuel à selectedMake comme:

 searchModel.selectedMake.subscribe(function (newMake) { if (newMake) { //ajax request } else { searchModel.availableModels([]); } }, searchModel); 

Cela ne changerait pas la fonctionnalité, mais un moyen plus explicite de souscrire à un seul changement observable.

Vous pouvez également choisir d’utiliser optionsValue: 'text' (ou ‘valeur’) dans la liaison et votre selectedMake sera défini sur le texte ou la valeur directement.

Si vos modèles étaient des enfants des objects make, vous pouvez même les lier à selectedMake().models (il serait nécessaire de se protéger contre selectedMake étant null, ce qui pourrait être fait à l’aide d’un DO, de la liaison de stream de contrôle 1.3, ou selectedMake() ? selectedMake().models : []

Je suis d’accord avec la réponse de Ryan.

En le prenant un peu sur une tangente connexe, je l’ai un peu remanié pour ne pas utiliser ajax et pour simplifier l’exemple (vous pouvez toujours l’append à nouveau). Mais voici un violon qui montre ce que vous cherchez à faire avec des exemples de données.

http://jsfiddle.net/johnpapa/vGg2h/