void Initialize()
        {
            _timingItemManager = null;//  new TimingItemManager () { Race = new Race() { Name = _details.Race, Code = _details.Race}, Location =  _details.Location, Token = _details.OurLittleSecret};

            _popover = new SettingsDialogViewController (_details.Location, _details.OurLittleSecret);
            UIPopoverController myPopOver = new UIPopoverController(_popover);
            _popover.Changed += () =>
            {
                _details.Location = _popover.Location;
                _details.OurLittleSecret = _popover.Secret;
            //				_timingItemManager = new TimingItemManager () { Race = new Race() { Name = _details.Race, Code = _details.Race}, Location =  _details.Location, Token = _details.OurLittleSecret};
                PopulateTable(true);
            };
            _popover.Clear += () =>
            {
                // _timingItemManager.Reset();
                _details.Reset();
                PopulateTable(false);
            };
            _popover.Save += () => {
            //				_timingItemManager.SaveItem (null);
                _popover.UpdateStatus(_timingItemManager.Status);
            };

            NavigationItem.RightBarButtonItem = new UIBarButtonItem("Settings", UIBarButtonItemStyle.Plain, null);
            NavigationItem.RightBarButtonItem.Clicked += (sender, e) => { myPopOver.PopoverContentSize = new SizeF(450f, 800f);
                myPopOver.PresentFromBarButtonItem (NavigationItem.RightBarButtonItem, UIPopoverArrowDirection.Left, true); };
            PopulateTable (true);
        }
        void Initialize()
        {
            _timingItemManager = null;            //  new TimingItemManager () { Race = new Race() { Name = _details.Race, Code = _details.Race}, Location =  _details.Location, Token = _details.OurLittleSecret};

            _popover = new SettingsDialogViewController(_details.Location, _details.OurLittleSecret);
            UIPopoverController myPopOver = new UIPopoverController(_popover);

            _popover.Changed += () =>
            {
                _details.Location        = _popover.Location;
                _details.OurLittleSecret = _popover.Secret;
//				_timingItemManager = new TimingItemManager () { Race = new Race() { Name = _details.Race, Code = _details.Race}, Location =  _details.Location, Token = _details.OurLittleSecret};
                PopulateTable(true);
            };
            _popover.Clear += () =>
            {
                // _timingItemManager.Reset();
                _details.Reset();
                PopulateTable(false);
            };
            _popover.Save += () => {
//				_timingItemManager.SaveItem (null);
                _popover.UpdateStatus(_timingItemManager.Status);
            };

            NavigationItem.RightBarButtonItem          = new UIBarButtonItem("Settings", UIBarButtonItemStyle.Plain, null);
            NavigationItem.RightBarButtonItem.Clicked += (sender, e) => { myPopOver.PopoverContentSize = new SizeF(450f, 800f);
                                                                          myPopOver.PresentFromBarButtonItem(NavigationItem.RightBarButtonItem, UIPopoverArrowDirection.Left, true); };
            PopulateTable(true);
        }
 TimingMasterDetailPage(TimingItemManager manager)
 {
     Master = new TimingMasterPage();
     Master.BindingContext = manager;
     Detail = new TimingDetailPage();
     Detail.BindingContext = manager;
     ((TimingDetailPage)Detail).TitleUpdated += (object sender, StringEventArgs e) =>
     {
         Title = string.Format("{0} {1}", manager.Title, e.Text);
     };
     Title = manager.Title;
 }
        LocationPickerPage(IRepository repo, IRace race)
        {
            // todo - summarise the race details
            Title = race.Code;

            Picker locationpicker = new Picker {
                WidthRequest = 300, Title = "Locations"
            };

            locationpicker.Items.Clear();
            repo.LocationList.Select(l => l.Name).ForEach(locationpicker.Items.Add);

            var entry = new Entry {
                Placeholder = "token"
            };

            var button = new Button {
                Text = "Go!", IsEnabled = false
            };

            // Accomodate iPhone status bar.
            this.Padding = new Thickness(10, Device.OnPlatform(20, 0, 0), 10, 5);

            Func <bool> enable = () => (!string.IsNullOrEmpty(_token) && locationpicker.SelectedIndex >= 0 && !string.IsNullOrEmpty(locationpicker.Items[locationpicker.SelectedIndex]));

            entry.TextChanged += (object sender, TextChangedEventArgs e) =>
            {
                _token           = entry.Text;
                button.IsEnabled = enable();
            };

            locationpicker.SelectedIndexChanged += (object sender, EventArgs e) =>
            {
                button.IsEnabled = enable();
            };

            button.Clicked += (object sender, EventArgs e) =>
            {
                IEnumerable <IBoat> boats = repo.BoatList;
                var location =
                    new LocationFactory()
                    .SetName(locationpicker.Items[locationpicker.SelectedIndex])
                    .SetToken(_token)
                    .SetItems(repo)
                    .Create();
                var tim = new TimingItemManager(new List <IRepository> {
                    repo
                }, location, boats);
                var page = TimingMasterDetailPage.Create(tim);

                Navigation.PushAsync(page);
            };

            var dump = new Button {
                Text = "Dump", IsEnabled = true
            };

            dump.Clicked += (object sender, EventArgs e) =>
            {
                repo.Dump();
            };


            Content = new StackLayout {
                Children =
                {
                    locationpicker,
                    entry,         button, dump
                }
            };
        }
 public static Page Create(TimingItemManager manager)
 {
     return(new TimingMasterDetailPage(manager));
 }
        public TimingDetailPage()
        {
            ReaderWriterLockSlim          locker = new ReaderWriterLockSlim();
            IDictionary <IBoat, DateTime> times  = new Dictionary <IBoat, DateTime>();

            Action updateTitle = () =>
            {
                var u = times.Count(t => t.Key.Number <= 0);
                var i = times.Count(t => t.Key.Number > 0 && t.Value > DateTime.MinValue);

                if (TitleUpdated != null)
                {
                    TitleUpdated(this, new StringEventArgs(string.Format(" - to save: {0} identified, {1} unidentified", i, u)));
                }
            };

            Action saveBoats = () =>
            {
                TimingItemManager manager = (TimingItemManager)BindingContext;
                try
                {
                    locker.EnterWriteLock();
                    manager.SaveBoat(times.Where(kvp => kvp.Value > DateTime.MinValue).Select(t => new Tuple <IBoat, DateTime, string>(t.Key, t.Value, string.Empty)));
                    times.Clear();
                    updateTitle();
                }
                finally
                {
                    locker.ExitWriteLock();
                }
            };
            Action <IBoat, bool> flipflop = (IBoat boat, bool seen) =>
            {
                try
                {
                    locker.EnterWriteLock();
                    boat.Seen = seen;
                    if (times.ContainsKey(boat))
                    {
                        times.Remove(boat);
                    }
                    times.Add(boat, seen ? DateTime.Now : DateTime.MinValue);
                    updateTitle();
                }
                finally
                {
                    locker.ExitWriteLock();
                }
            };
            Action unidentified = () =>
            {
                flipflop(((TimingItemManager)BindingContext).UnidentifiedBoat, true);
            };
//          var anchor = new ToolbarItem("Anchor", "Anchor.png", () => Debug.WriteLine("anchor"), priority: 3);
            var         plus           = new ToolbarItem("Add", "Add.png", () => unidentified(), priority: 3);
            var         sync           = new ToolbarItem("Sync", "Syncing.png", saveBoats, priority: 2);
            ToolbarItem more           = null;
            Action      refreshToolbar = () =>
            {
                ToolbarItems.Clear();
                ToolbarItems.Add(plus);
                ToolbarItems.Add(sync);
                ToolbarItems.Add(more);
            };

            more = new ToolbarItem("More", "More.png", refreshToolbar, priority: 1);
            refreshToolbar();



            var listView = new ListView();

            listView.SetBinding(ListView.ItemsSourceProperty, "Unfinished");
            Action <IBoat> press = async(IBoat boat) =>
            {
                string pin   = "Pin to top";
                string send  = "Send to End";
                var    sheet = await DisplayActionSheet(string.Format("Boat {0}: Send to ... ?", boat.Number), "Cancel", null, pin, send);

                if (sheet == pin)
                {
                    ToolbarItem item   = null;
                    Action      action = () =>
                    {
                        flipflop(boat, true);
                        ToolbarItems.Remove(item);
                    };
                    item = new ToolbarItem(boat.Number.ToString(), null, action, priority: -1);

                    ToolbarItems.Add(item);
                }
                if (sheet == send)
                {
                    boat.End = true;
                }
                Debug.WriteLine("Action: " + sheet);
            };

            listView.ItemTemplate     = new DataTemplate(() => new UnseenCell(press));
            listView.PropertyChanged += (object sender, System.ComponentModel.PropertyChangedEventArgs e) =>
            {
                Debug.WriteLine("underlying change");
            };
            listView.ItemSelected += (object sender, SelectedItemChangedEventArgs e) =>
            {
                if (e.SelectedItem == null)
                {
                    return;
                }
                IBoat boat = (IBoat)e.SelectedItem;
                flipflop(boat, !boat.Seen);
                listView.SelectedItem = null;
            };
            SearchBar searchBar = new SearchBar
            {
                Placeholder = "Filter list",
            };

            searchBar.TextChanged += (object sender, TextChangedEventArgs e) =>
            {
                TimingItemManager manager = (TimingItemManager)BindingContext;
                manager.Filter(searchBar.Text);
            };
            Content = new StackLayout()
            {
                Children = { searchBar, listView }
            };

            // idea: hide a non-starter
        }