0

I am working on an App that requires one list view having text labels with NSUnderlineStyle on user deletion. As per the requirement user have Delete/restore option in detail screen. On delete confirmation the text label should be underline style for that particular cell.

I am using LabelRenderer for NSUnderlineStyle in Xamarin iOS.

But currently ListView displays text Labels with underline style which is not deleted by user on list view scroll. The underline style are swapping from one cell label to another on list view scroll.

Below my sample code.

protected override void OnElementPropertyChanged(object sender, PropertyChangedEventArgs e)
{
    base.OnElementPropertyChanged(sender, e);

    if (this.Control == null)
    {
        return;
    }

    if (this.Element is ExtendedLabel extended)
    {
        var strikethroughStyle = extended.IsStrikeThrough ? NSUnderlineStyle.Single : NSUnderlineStyle.None;
        this.Control.AttributedText = new NSMutableAttributedString(
            extended.Text ?? string.Empty,
            this.Control.Font,
            strikethroughStyle: strikethroughStyle);
    }
}
ToolmakerSteve
  • 18,547
  • 14
  • 94
  • 196
  • the essential symptom is “underline styles are swapping from one cell to another when scrolling”. To debug this, edit question to show the entire custom renderer .cs - you’ll need some change elsewhere in that. Also, show the xaml of the listview or collectionview that contains these entries. – ToolmakerSteve Dec 08 '21 at 18:03

1 Answers1

0

This is the common issue of TableView Cell Resue , tableView will reuse the cell for the visible(inside screen shot) ones , so it would show the previous style .

To solve this we can forcedly set the style each time when the cell is going to display .

Create custom renderer for ListView , and do this in WillDisplay method ,before it we need to override TableView's Delegate.

[assembly: ExportRenderer(typeof(ListView), typeof(MyRenderer))]
namespace FormsApp.iOS
{

    public class MyDelegate : UITableViewDelegate
    {
        List<Model> data;
        public MyDelegate(List<Model> _data)
        {
            data = _data;
        }

        public override void WillDisplay(UITableView tableView, UITableViewCell cell, NSIndexPath indexPath)
        {
            var views = cell.ContentView.Subviews;

            foreach (var view in views)
            {
                if(view is LabelRenderer renderer)
                {
                    UILabel label = renderer.Control;
                    var strikethroughStyle = data[indexPath.Row].YourProperty?NSUnderlineStyle.Single : NSUnderlineStyle.None;
                    label.AttributedText = new NSMutableAttributedString(
                        label.Text ?? string.Empty,
                        label.Font,
                        strikethroughStyle: strikethroughStyle);
                }
            }
        }
    }

    public class MyRenderer : ListViewRenderer
    {
        protected override void OnElementChanged(ElementChangedEventArgs<ListView> e)
        {
            base.OnElementChanged(e);

            if (e.OldElement != null)
            {
                // Unsubscribe
            }

            if (e.NewElement != null)
            {
                IEnumerable<Model> data = (IEnumerable<Model>)Element.ItemsSource;
                Control.Delegate = new MyDelegate(data.ToList());
            }
        }
    }   
}
ColeX
  • 14,062
  • 5
  • 43
  • 240