I've been chasing down an elusive problem for some time now and I've narrowed it to a logic change in the ListViewItemBinder.refresh() method between Kendo UI versions 2015.2.902 and 2015.3.930 (the issue happens on every version since 2015.3.930). We have a mobile list view that is bound to a data source. The template for the ListView creates a Touch widget and a tap handler for each list item. The tap events and event handlers are working just fine, within this tap handler we change several properties on the data items within the DataSource. The issue is that in v2015.2.902 these property changes cause the ListView to refresh itself and properly reflect those property changes, but in 2015.3.930 the ListView does *not* refresh itself even though the code has not changed on our end.
I finally managed to isolate the issue to a logic change within ListViewItemBinder.refresh() between the two versions, specifically within the first "if" block. Here's the logic in 2015.2.902:
if
(action ===
"itemchange"
&& !listView._hasBindingTarget()) {
item = listView.findByDataItem(dataItems)[0];
if
(item) {
listView.setDataItem(item, dataItems[0]);
}
return
;
}
In 2015.2.902, action === "itemchange" resolves to true and !listView._hasBindingTarget()) resolves to false, so this block is skipped. The code eventually drops to the following if/else if/else blocks and eventually calls the very last "else" block which actually triggers the kendo code that re-executes the template and replaces the HTML content (comment is mine):
if
(action ===
"add"
&& !groupedMode) {
var
index = view.indexOf(dataItems[0]);
if
(index > -1) {
addedItems = listView.insertAt(dataItems, index);
addedDataItems = dataItems;
}
}
else
if
(action ===
"remove"
&& !groupedMode) {
addedItems = [];
listView.remove(dataItems);
}
else
if
(groupedMode) {
listView.replaceGrouped(view);
}
else
if
(prependOnRefresh && !listView._filter) {
addedItems = listView.prepend(view);
addedDataItems = view;
}
else
{
listView.replace(view);
// <-- This is where the template is re-executed
}
However, in v2015.3.930, the first "if" block I listed earlier was re-written as follows:
if
(action ===
"itemchange"
) {
// action is indeed "itemchange"
if
(!listView._hasBindingTarget()) {
// This evaluates to false
item = listView.findByDataItem(dataItems)[0];
if
(item) {
listView.setDataItem(item, dataItems[0]);
}
}
return
;
// We hit this return statement, thus the "refresh" block is never called
}
As I mentioned in the comments, this logic change causes us to immediately hit the "return" statement and we never drop into the lower if/else if/else block where the template gets re-executed. My questions then are as follows:
- What exactly was the purpose of this change?
- Is the scenario I've laid out actually exposing a bug, or is there something that I'm doing incorrectly that I can resolve within my own code?
I've tried to mock up this scenario in the Dojo but as of yet haven't quite been able to do it, hence the long post. Thanks for taking a look!