Invalidate layout on ViewCell if Measurements change (#7755)

This commit is contained in:
Shane Neuville 2019-10-01 09:21:08 -06:00 коммит произвёл Rui Marinho
Родитель 16504ee052
Коммит ffb1992ed6
4 изменённых файлов: 45 добавлений и 1 удалений

Просмотреть файл

@ -30,7 +30,7 @@ namespace Xamarin.Forms.Controls.Issues
var cell = new DataTemplate (typeof(CustomCell));
var listView = new ListView {
var listView = new ListView(ListViewCachingStrategy.RecycleElement) {
ItemsSource = presidents,
ItemTemplate = cell,
RowHeight = 200

Просмотреть файл

@ -1,4 +1,5 @@
using System;
using System.ComponentModel;
using UIKit;
using Xamarin.Forms.Internals;
using Xamarin.Forms.PlatformConfiguration.iOSSpecific;
@ -10,6 +11,7 @@ namespace Xamarin.Forms.Platform.iOS
static readonly BindableProperty RealCellProperty = BindableProperty.CreateAttached("RealCell", typeof(UITableViewCell), typeof(Cell), null);
EventHandler _onForceUpdateSizeRequested;
PropertyChangedEventHandler _onPropertyChangedEventHandler;
public virtual UITableViewCell GetCell(Cell item, UITableViewCell reusableCell, UITableView tv)
{
@ -89,8 +91,12 @@ namespace Xamarin.Forms.Platform.iOS
protected void WireUpForceUpdateSizeRequested(ICellController cell, UITableViewCell nativeCell, UITableView tableView)
{
var inpc = cell as INotifyPropertyChanged;
cell.ForceUpdateSizeRequested -= _onForceUpdateSizeRequested;
if (inpc != null)
inpc.PropertyChanged -= _onPropertyChangedEventHandler;
_onForceUpdateSizeRequested = (sender, e) =>
{
var index = tableView?.IndexPathForCell(nativeCell) ?? (sender as Cell)?.GetIndexPath();
@ -98,7 +104,30 @@ namespace Xamarin.Forms.Platform.iOS
tableView.ReloadRows(new[] { index }, UITableViewRowAnimation.None);
};
_onPropertyChangedEventHandler = (sender, e) =>
{
if(e.PropertyName == "RealCell" && sender is BindableObject bo && GetRealCell(bo) == null)
{
if(sender is ICellController icc)
icc.ForceUpdateSizeRequested -= _onForceUpdateSizeRequested;
if (sender is INotifyPropertyChanged notifyPropertyChanged)
notifyPropertyChanged.PropertyChanged -= _onPropertyChangedEventHandler;
_onForceUpdateSizeRequested = null;
_onPropertyChangedEventHandler = null;
}
};
cell.ForceUpdateSizeRequested += _onForceUpdateSizeRequested;
if (inpc != null)
inpc.PropertyChanged += _onPropertyChangedEventHandler;
}
void Ncp_PropertyChanged(object sender, PropertyChangedEventArgs e)
{
System.Diagnostics.Debug.WriteLine($"{e.PropertyName}");
}
internal static UITableViewCell GetRealCell(BindableObject cell)

Просмотреть файл

@ -108,6 +108,7 @@ namespace Xamarin.Forms.Platform.iOS
if (_cell != null)
{
_cell.PropertyChanged -= HandlePropertyChanged;
CellRenderer.SetRealCell(_cell, null);
}
_cell = null;
}

Просмотреть файл

@ -9,6 +9,10 @@ namespace Xamarin.Forms.Platform.iOS
{
public class ViewCellRenderer : CellRenderer
{
public ViewCellRenderer()
{
}
public override UITableViewCell GetCell(Cell item, UITableViewCell reusableCell, UITableView tv)
{
Performance.Start(out string reference);
@ -141,6 +145,8 @@ namespace Xamarin.Forms.Platform.iOS
if (_viewCell != null)
{
_viewCell.PropertyChanged -= ViewCellPropertyChanged;
_viewCell.View.MeasureInvalidated -= OnMeasureInvalidated;
SetRealCell(_viewCell, null);
}
_viewCell = null;
}
@ -170,6 +176,7 @@ namespace Xamarin.Forms.Platform.iOS
{
Device.BeginInvokeOnMainThread(oldCell.SendDisappearing);
oldCell.PropertyChanged -= ViewCellPropertyChanged;
oldCell.View.MeasureInvalidated -= OnMeasureInvalidated;
}
_viewCell = cell;
@ -201,9 +208,16 @@ namespace Xamarin.Forms.Platform.iOS
Platform.SetRenderer(_viewCell.View, renderer);
UpdateIsEnabled(_viewCell.IsEnabled);
_viewCell.View.MeasureInvalidated += OnMeasureInvalidated;
Performance.Stop(reference);
}
void OnMeasureInvalidated(object sender, EventArgs e)
{
SetNeedsLayout();
}
}
}
}