Search code examples
iosxamarinxamarin.iosicarousel

Xamarin ios iCarousel use (I need carousel to cycle and set the cycle time )


I recently used Carousel for my work. The downloaded sample can show the feeling I want. But I need carousel to cycle play and set the cycle time I don't know how to use iCarouselDelegate to rewrite the method. Please give me some advice.

namespace Xamarin.iOS.iCarouselExample { public partial class ViewController : UIViewController { protected ViewController(IntPtr handle) : base(handle) { }

                private List<int> items;

                public override void ViewDidLoad()
                {
                    base.ViewDidLoad();

                    items = Enumerable.Range(1, 100).ToList();

                    // Setup iCarousel view
                    var carousel = new iCarousel
                    {
                        Bounds = View.Bounds,

                        ContentMode = UIViewContentMode.Center,
                        Type = iCarouselType.TimeMachine,
                        Frame = View.Frame,
                        CenterItemWhenSelected = true,
                        DataSource = new SimpleDataSource(items),
                        Delegate = new SimpleDelegate(this)
                    };

                    View.AddSubview(carousel);
                    ViewDidLayoutSubviews();
                }

                public class SimpleDataSource : iCarouselDataSource
                {
                    private readonly List<int> _data;

                    public SimpleDataSource(List<int> data)
                    {
                        _data = data;
                    }

                    public override nint NumberOfItemsInCarousel(iCarousel carousel) => _data.Count;

                    public override UIView ViewForItemAtIndex(iCarousel carousel, nint index, UIView view)
                    {
                        UILabel label;

                        // create new view if no view is available for recycling
                        if (view == null)
                        {
                            var imgView = new UIImageView(new RectangleF(0, 200, 200, 200))
                            {
                                BackgroundColor = UIColor.Orange,
                                ContentMode = UIViewContentMode.Center
                            };

                            label = new UILabel(imgView.Bounds)
                            {
                                BackgroundColor = UIColor.Clear,
                                TextAlignment = UITextAlignment.Center,
                                Tag = 1
                            };
                            imgView.AddSubview(label);
                            view = imgView;
                        }
                        else
                        {
                            // get a reference to the label in the recycled view
                            label = (UILabel)view.ViewWithTag(1);
                        }

                        label.Text = _data[(int)index].ToString();

                        return view;
                    }
                }

                public class SimpleDelegate : iCarouselDelegate
                {
                    private readonly ViewController _viewController;

                    public SimpleDelegate(ViewController vc)
                    {
                        _viewController = vc;
                    }

                    public override void DidSelectItemAtIndex(iCarousel carousel, nint index)
                    {
                        var alert = UIAlertController.Create("Clicked index:", index.ToString(), UIAlertControllerStyle.Alert);
                        alert.AddAction(UIAlertAction.Create("Ok", UIAlertActionStyle.Cancel, null));

                        _viewController.PresentViewController(alert, animated: true, completionHandler: null);
                    }

                    public override nfloat ValueForOption(iCarousel carousel, iCarouselOption option, nfloat value)
                    {
                        option.Wrap = true;
                    }

                }
            }
        }

Solution

  • You can just run a loop in a background thread and assign the change to the CurrentItemIndex in the UI/main thread.

    Something like this at the end of your ViewDidLoad (in the ICarousel example) will work:

     Task.Run(async () =>
     {
         while (carousel.CurrentItemIndex < 100)
         {
             InvokeOnMainThread(() => carousel.CurrentItemIndex++);
             await Task.Delay(1000);
         }
     });
    

    Note: Xamarin.iOS regrettably never has implemented "Dynamic" (@dynamic/NSManaged) properties that CoreData/CoreAnimation/etc... can make use of, but if you review the links below, I show how I implement them within Xamarin and thus can do things such as:

    UIView.Animate(1.0, 1.0, UIViewAnimationOptions.Autoreverse,
        () => { carousel.CurrentItemIndex = 100; },
        () => { }
    );