knockout.js - knockout js: initializing value of dropdown that is nested in an observableArray -
i have seen solutions elsewhere problem, have not yet found how make work in specific circumstances.
an observablearray populates html list. inside list, user can edit 1 of values particular row. item edited in row observablearray populates dropdown list. array drop down list populated via ajax call when edit button on row clicked (edit button not shown in code below).
i have working fine, except 1 important issue: of yet, value in dropdown list not being pre-populated.
below gross mockup of real code doing.
if call selectedteamtype
selectedteamtype()
in html, intial value is populated, further changes select box not registered. if call selectedteamtype
selectedteamtype
, intial value not set properly, further changes select box are registered.
html
<table> <tr> <!-- ko foreach: my.teamviewmodel.teams --> <td data-bind="text: teamid"></td> <td data-bind="text: teamtext"></td> <td> <!-- teamtype editable, provide dropdown list, default current value --> <select data-bind="options: my.teamviewmodel.teamtypes, optionstext: 'teamtypetext', optionsvalue: 'teamtypeid', value: selectedteamtype"></select> </td> </tr> <!-- /ko --> </table>
javascript
var = || {}; $(function () { my.teammodel = function () { var self = this; self.teamid = ko.observable(); self.teamtext = ko.observable(); self.teamtypeid = ko.observable(); self.selectedteam = ko.observable(); self.edit = function () { my.teamviewmodel.load_teamtypes(); }; }; my.teamtypesmodel = function () { var self = this; self.teamtypeid = ko.observable(); self.teamtypetext = ko.observable(); }; my.teamviewmodel = function () { var teams = ko.observablearray([]), teamtypes = ko.observablearray([]), load_teamtypes = function () { $.ajax({ // part of ajax call displayed here sake of brevity... $.each(data, function (i, d) { teamtypes.push(new my.teamtypesmodel() .teamtypeid(d.teamtypeid) .teamtypetext(d.teamtypetext) ); }); }); }, load_teams = function () { $.ajax({ // part of ajax call displayed here sake of brevity... $.each(data, function (i, d) { teams.push(new my.teammodel() .teamid(d.teamid) .teamtext(d.teamtext) ); }); } }); }; return { teams: teams, teamtypes: teamtypes, load_teamtypes: load_teamtypes }; } (); my.teamviewmodel.load_teams(); ko.applybindings(my.teamviewmodel);
});
is selectedteamtype
set before my.teamviewmodel.teamtypes
array populated? if so, why initial value not being set. don't see anywhere in javascript posted setting initial value of selectedteamtype
.
update
your answer own question confirmed suspicion above. there reason why need load team types dropdown every time user goes edit team? if select options same every team, why not load once?
example:
my.teamviewmodel.load_teams(); my.teamviewmodel.load_teamtypes(); ko.applybindings(my.teamviewmodel);
this way, options list should loaded time user clicks edit button. save client/server sweat too, if fresh team types options list not needed every team in list.
if want guarantee both $.ajax
calls complete before anything, suggest looking jquery's $.deferred
method , promise api. when have more 1 $.ajax
call, , need perform action after both have succeeded, can this:
var defer_teams = $.deferred(); var defer_teamtypes = $.deferred(); $.ajax({ // initiate server call teams url: '/teams', success: function(data) { defer_teams.resolve(data); // tell promise api ready } }); $.ajax({ // initiate server call team types url: '/team-types', success: function(data) { defer_teamtypes.resolve(data); // tell promise api ready } }); $.when(defer_teams, defer_teamtypes).then(function(teamdata, teamtypedata) { $.each(teamtypedata, function(i, d) { // populate team types array // ko.mapping instead of $.each }) $.each(teamdata, function(i, d) { // populate teams array // ko.mapping instead of $.each }) });
say /teams call returns fast, /team-types call lags. above, teams array not populated until both calls finish. , need types call finish before user can click edit button , selected value pre-populated.
Comments
Post a Comment