I have previoiusly posted and solved my problem here, but now when i tried to put that solution in my orignal application i'm facing difficulties, again the dropdowns are not working as they are working in testing page, this is my code
this is my previous question
<table class="ListViewtable-minimal grid-100 mobile-grid-100">
<thead>
<tr>
<th>S. No.</th>
<th>Action</th>
<th>Code</th>
<th>Product</th>
<th>Quantity</th>
<th>Offers</th>
<th>Stock Quantity</th>
<th>Packing</th>
<th>Rate</th>
<th>Total Price</th>
</tr>
</thead>
<tbody data-bind='foreach: {data: details,beforeRemove: hideRow,afterAdd: showRow}'>
<tr>
<td><span data-bind='text : $index() + 1'></span> </td>
<td><a href="#" data-bind='click: remove'> <img src="../../Assets/img/delete.png" alt="x" /></a> </td>
<td><input type="text" data-bind='value: ProductCode' class="txtbx" style="width:100px;"/></td>
<td>
<input type="hidden" data-bind='value: ID' />
<select data-bind="options: Products, optionsText: 'Name',optionsValue: 'ID', value: ProductID, optionsCaption: '-'" />
</td>
<td><input type="text" data-bind='value: Quantity' class="txtbx" style="width:50px;"/></td>
<td data-bind="if: ProductID">
<select data-bind="options: ProductOffers, optionsText: 'Name',optionsValue: 'ID', value: ProductOfferID, optionsCaption: '-'" />
</td>
<td><input type="text" data-bind='value: StockQuantity' class="txtbx" style="width:50px;"/> </td>
<td><input type="text" data-bind='value: ProductPacking' class="txtbx" style="width:50px;"/> </td>
<td><input type="text" data-bind='value: ProductRate' class="txtbx" style="width:80px;"/> </td>
<td><input type="text" data-bind='value: TotalPrice' class="txtbx" style="width:120px;"/> </td>
</tr>
</tbody>
<tfoot>
<tr>
<td colspan="2">Totals</td>
<td colspan="2"></td>
<td data-bind='text: totalQuantity'></td>
<td></td>
<td></td>
<td></td>
<td></td>
<td></td>
</tr>
</tfoot>
</table>
</div>
</div>
<div>
<button runat="server" id="btnAddService" type="submit" class="fleft" data-bind="click: add" >Add New</button>
<button runat="server" id="btnSaveTop" data-bind="click: save" type="submit" class="fright">Save</button>
<asp:Button ID="btnBackTop" runat="server" Text="Back" UseSubmitBehavior="false" CssClass="fright"/>
</div>
<script type="text/javascript">
this.showRow = function (element) {
if (element.nodeType === 1) {
$(element).hide().fadeIn('fast');
}
};
this.hideRow = function (element) {
if (element.nodeType === 1) {
$(element).fadeOut(function () { $(element).remove(); });
}
};
function isNumber(n) {
if (typeof n != "undefined") {
return !isNaN(parseFloat(n)) && isFinite(n);
}
else {
return false;
}
}
function showMessage(msg) {
//msg.d contains the success status
if (typeof (msg) != "undefined" && msg != null && msg.d != null && msg.d.length == 0) {
//success message here
setTimeout("window.location = 'index.aspx?ID=" + viewModel.MasterID + "';", 1500);
}
else {
//Error Message Here
}
}
function Product(id, name) {
this.ID = id;
this.Name = name;
}
//Constructor
function Details(o) {
var self = this;
if (typeof o != "undefined") {
alert("Constructor called, filled from DB");
self.ID = ko.observable(o.ID);
self.ProductCode = ko.observable(o.ProductCode);
self.Products = ko.observableArray(<%= LoadProducts() %>),
self.ProductOffers = ko.observableArray(GetProductOffers(self.ProductID))
self.ProductID = ko.observable(o.ProductID).extend({ numeric: 0 });
self.ProductOfferID = ko.observable(o.ProductOfferID).extend({ numeric: 0 });
self.Quantity = ko.observable(o.Quantity).extend({ numeric: 0 });
self.StockQuantity = ko.observable(o.StockQuantity).extend({ numeric: 0 });
self.ProductPacking = ko.observable(o.ProductPacking).extend({ numeric: 0 });
self.ProductRate = ko.observable(o.ProductRate).extend({ numeric: 0 });
self.TotalPrice = ko.observable(o.TotalPrice).extend({ numeric: 0 });
self.remove = function (data) {
if (confirm('This record will be deleted from the source, Are you sure ?')) {
//Data is deleted via ajax
}
}
}
else {
alert("Constructor called");
self.ID = ko.observable('0');
self.ProductCode = ko.observable('');
self.Products = ko.observableArray(<%= LoadProducts() %>),
self.ProductOffers = ko.observableArray([])
self.ProductID = ko.observable('0').extend({ numeric: 0 });
self.ProductOfferID = ko.observable('0').extend({ numeric: 0 });
self.Quantity = ko.observable('0').extend({ numeric: 0 });
self.StockQuantity = ko.observable('1').extend({ numeric: 0 });
self.ProductPacking = ko.observable('0').extend({ numeric: 0 });
self.ProductRate = ko.observable('0').extend({ numeric: 0 });
self.TotalPrice = ko.observable('0').extend({ numeric: 0 });
self.remove = function (data) {
if (confirm('Are you sure you want to delete this record ?'))
viewModel.details.remove(this);
}
}
}
//Building ViewModel
var viewModel = {
MasterID: 0,
ProductID: ko.observable('0'),
details: ko.observableArray([]),
add: function () {
this.details.push(new Details());
},
load: function (data, MasterID) {
this.MasterID = MasterID;
if (data.length == 0) {
var totalRows = jQuery(".hfNumberOfRows").val();
if (totalRows != 0) {
for (var i = 0; i < totalRows; i++) {
this.details.push(new Details());
}
}
else {
this.details.push(new Details());
}
}
else {
for (i = 0; i < data.length; i++) {
this.details.push(new Details(data[i]));
}
}
},
save: function () {
}
}
viewModel.ProductID.subscribe(function (newValue) {
viewModel.ProductOffers.removeAll();
alert(newValue);
if (newValue) {
var productOffers = GetProductOffers(newValue);
viewModel.ProductOffers(productOffers);
alert(viewModel.ProductOffers());
}
});
viewModel.totalQuantity = ko.computed(function () {
var result = 0;
ko.utils.arrayForEach(this.details(), function (item) {
if (isNumber(item.Quantity())) {
result += parseFloat(item.Quantity());
}
});
return result;
}, viewModel);
ko.extenders.numeric = function (target, precision) {
//create a writeable computed observable to intercept writes to our observable
var result = ko.computed({
read: target, //always return the original observables value
write: function (newValue) {
var current = target(),
roundingMultiplier = Math.pow(10, precision),
newValueAsNum = isNaN(newValue) ? 0 : parseFloat(+newValue),
valueToWrite = Math.round(newValueAsNum * roundingMultiplier) / roundingMultiplier;
//only write if it changed
if (valueToWrite !== current) {
target(valueToWrite);
} else {
//if the rounded value is the same, but a different value was written, force a notification for the current field
if (newValue !== current) {
target.notifySubscribers(valueToWrite);
}
}
}
});
//initialize with current value to make sure it is rounded appropriately
result(target());
//return the new computed observable
return result;
};
//Init Loading
jQuery(document).ready(function () {
//Ajax call gets the data from database in json form
});
function GetProductOffers(ProductID) {
alert("Ajax call initiated.");
var Val = "here ajax call is initiated";
return Val;
}
//Binding ViewModel
ko.applyBindings(viewModel);
</script>
I think this portion of the code needs to be modified according to current scenario, I'm not getting the alert for newValue
or viewModel.ProductOffers()
viewModel.ProductID.subscribe(function (newValue) {
viewModel.ProductOffers.removeAll();
alert(newValue);
if (newValue) {
var productOffers = GetProductOffers(newValue);
viewModel.ProductOffers(productOffers);
alert(viewModel.ProductOffers());
}
});