In my application I am trying to integrate bootstrap and knockout into MVC4. I have two drop-down controls from where the user can select an item and then I use jQuery to populate the textbox next to that. This works without issue when I use ViewBag and a @foreach loop but when I try to use knockout observables I am having an issue.
I am able to see the data from my ViewModel show up in the drop down control but it will not update that value in the text box. Is there a special data-bind attribute I should be using?
Some code...
<div class="container">
<div class="col-sm-7 well">
<form class="form-inline" action="#" method="get">
<div class="input-group col-sm-8">
<input class="form-control" value="" placeholder="Work Section" name="q" type="text">
<div class="input-group-btn">
<button type="button" class="btn btn-default dropdown-toggle" data-toggle="dropdown">Select <span class="caret"></span></button>
<ul class="dropdown-menu">
<li data-bind="foreach: Names">
<a href="#" data-bind="text: Name, value: Name"></a>
</li>
</ul>
<input name="category" class="category" type="hidden">
</div>
</div>
<div class="input-group col-sm-8">
<input class="form-control item" value="" placeholder="Select a Color" name="color" type="text">
<div class="input-group-btn">
<button type="button" class="btn btn-default dropdown-toggle item" data-toggle="dropdown">Select <span class="caret"></span></button>
<ul class="dropdown-menu">
@foreach (var item in ViewBag.Colors)
{
<li>
<a href="#">@item</a>
</li>
}
</ul>
<input name="category" class="category" type="hidden">
</div>
</div>
The issue is with the Names foreach as the Colors is working fine.
I am using this to find the control on the page and take the selected item and place that in the input control...I have verified this now only works on the Colors dropdown.
$(function () {
$(".dropdown-menu li a").click(function () {
$(this).parents(".input-group").find('.form-control').text($(this).text());
$(this).parents(".input-group").find('.form-control').val($(this).text());
});
});
I have tried both approaches below to no avail. Let's start with the first response....
I placed the following in my tag at the top of the page
$(function ViewModel() {
alert('Here'); // To test if the code generating the model is executed
this.Names = [{ name: "Person 1", name: "Person 2" }];
this.selectedName = ko.observable();
this.clickName = function (name) { this.selectedName = name; }
});
Next I placed a new at the top of my page:
<p>Current selection is <span data-bind="text: selectedName"></span></p>
Lastly, I placed this code in the bootstrap dropdown:
<ul class="dropdown-menu" data-bind="foreach: Names">
<li class="dropdown">
<a href="#" data-bind="text: Name, value: Name, click: clickName(Name)"></a>
</li>
</ul>
The drop down is empty and the div never gets updated.
OK, after taking the ViewModel I created and integrating the click: function() {$root.Name(Name);} I am now able to see my value update as I hoped.
Here is my view model code
$(document).ready(function () {
function ViewModel() {
var self = this;
self.Name = ko.observable("");
var Names = {
Name: self.Name
};
self.Name = ko.observable();
self.Names = ko.observableArray([{ Name: "Brian" }, { Name: "Jesse" }, {Name: "James"}]);
}
var viewModel = new ViewModel();
ko.applyBindings(viewModel);
});