diff --git a/apps/tests/ui/proxy-view-container/proxy-view-container-tests.ts b/apps/tests/ui/proxy-view-container/proxy-view-container-tests.ts
index 5ef727832..d140d3dcb 100644
--- a/apps/tests/ui/proxy-view-container/proxy-view-container-tests.ts
+++ b/apps/tests/ui/proxy-view-container/proxy-view-container-tests.ts
@@ -8,6 +8,7 @@ import {LayoutBase} from "ui/layouts/layout-base"
import {StackLayout} from "ui/layouts/stack-layout"
import {GridLayout} from "ui/layouts/grid-layout"
import {ProxyViewContainer} from "ui/proxy-view-container";
+import {ListView} from "ui/list-view";
export function test_add_children_to_attached_proxy() {
var outer = new StackLayout();
@@ -224,6 +225,25 @@ export function test_proxy_iniside_border() {
helper.buildUIAndRunTest(scroll, testAction);
}
+export function test_proxy_iniside_listview_itemtemplate_crash() {
+ // Usually reproducible with an Angular component in the template
+ // We use a simple declaration here to simulate it.
+ var list = new ListView();
+ list.items = ["item 1"];
+ list.itemTemplate = `
+
+
+
+ `;
+
+ function testAction(views: Array) {
+ var page = views[1];
+ waitUntilElementLayoutIsValid(page);
+ };
+
+ helper.buildUIAndRunTest(list, testAction);
+}
+
// TODO: Proxy as a direct child to of TabItem is not supported. Not sure if we want to support it.
//export function test_proxy_iniside_tab() {
// var proxy = new ProxyViewContainer();
diff --git a/ui/list-view/list-view.android.ts b/ui/list-view/list-view.android.ts
index f1235929c..00aad53d8 100644
--- a/ui/list-view/list-view.android.ts
+++ b/ui/list-view/list-view.android.ts
@@ -6,6 +6,7 @@ import proxy = require("ui/core/proxy");
import dependencyObservable = require("ui/core/dependency-observable");
import definition = require("ui/list-view");
import utils = require("utils/utils")
+import {ProxyViewContainer} from "ui/proxy-view-container";
import * as layoutBase from "ui/layouts/layout-base";
import * as colorModule from "color";
@@ -229,7 +230,10 @@ function ensureListViewAdapterClass() {
}
this._listView._prepareItem(args.view, index);
if (!args.view.parent) {
- if (args.view instanceof layoutBase.LayoutBase) {
+ // Proxy containers should not get treated as layouts.
+ // Wrap them in a real layout as well.
+ if (args.view instanceof layoutBase.LayoutBase &&
+ !(args.view instanceof ProxyViewContainer)) {
this._listView._addView(args.view);
convertView = args.view.android;
} else {
diff --git a/ui/list-view/list-view.ios.ts b/ui/list-view/list-view.ios.ts
index 5c978798c..668aacc68 100644
--- a/ui/list-view/list-view.ios.ts
+++ b/ui/list-view/list-view.ios.ts
@@ -4,6 +4,8 @@ import common = require("./list-view-common");
import utils = require("utils/utils");
import view = require("ui/core/view");
import proxy = require("ui/core/proxy");
+import {StackLayout} from "ui/layouts/stack-layout";
+import {ProxyViewContainer} from "ui/proxy-view-container";
import dependencyObservable = require("ui/core/dependency-observable");
import * as colorModule from "color";
@@ -322,11 +324,18 @@ export class ListView extends common.ListView {
let args = notifyForItemAtIndex(this, cell, view, ITEMLOADING, indexPath);
view = args.view || this._getDefaultItemContent(indexPath.row);
+ // Proxy containers should not get treated as layouts.
+ // Wrap them in a real layout as well.
+ if (view instanceof ProxyViewContainer) {
+ var sp = new StackLayout();
+ sp.addChild(view);
+ view = sp;
+ }
+
// If cell is reused be have old content - remove it first.
if (!cell.view) {
cell.owner = new WeakRef(view);
- }
- else if (cell.view !== view) {
+ } else if (cell.view !== view) {
this._removeContainer(cell);
(cell.view._nativeView).removeFromSuperview();
cell.owner = new WeakRef(view);
@@ -341,8 +350,7 @@ export class ListView extends common.ListView {
}
cellHeight = this._layoutCell(view, indexPath);
- }
- finally {
+ } finally {
this._preparingCell = false;
}
return cellHeight;