locked
ListView only updating with screen rotation RRS feed

  • Question

  • User366410 posted

    After a user logs in, I create a master / detail page

    App.cs ``` public static MasterDetailPage GetHomePage() { var page = new MasterDetailPage() { Master = new NavigationPage(new MainSideMenuPage()) { Title = "Menu", BarBackgroundColor = Color.FromHex("333333") }, Detail = new NavigationPage( new TabbedPage() { Children = { new MainPage(), new MainTrendingPage(), new MainExplorePage() }, BarBackgroundColor = Color.FromHex("FFFFFF"), BarTextColor = Color.Black,

                })
                    {
                        BarBackgroundColor = Color.FromHex("333333"),
                    }
            };
    
            return page;
        }
    

    ```

    Login.cs private async void ValidLogin() { App.Current.MainPage = App.GetHomePage(); await Navigation.PopToRootAsync(); }

    Once the login is finished, the Tabbed page opens up, but the ListView is blank. However, when I rotate from portrait to landscape, I see all of my items appear. When I rotate back to portrait, they disappear. Conversely, if I start in landscape from the login, and rotate to portrait, I see all the items in portrait, but they disappear in landscape. Since I see the items after rotation, I'm pretty sure my code for getting the items is working fine.

    I suspect I'm not updating the bindings correctly (new to this)?

    Everything works fine if I define a static ObservableCollection from the beginning.

    MainPageViewModel.cs ``` public class MainPageViewModel : INotifyPropertyChanged { public event PropertyChangedEventHandler PropertyChanged; private ObservableCollection _Results;

        public ObservableCollection<HomePageResult> Results
        {
            get
            {
                return _Results;
            }
            set
            {
                _Results = value;
                OnPropertyChanged("Results");
            }
        }
    
        protected virtual void OnPropertyChanged(string propertyName)
        {
            PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
        }
    
        public MainPageViewModel()
        {
            _Results = new ObservableCollection<HomePageResult>();
        }
    
        public async void GetStuff()
        {
            Connection service = new Connection();
            var response = await service.GetObject<List<Item>>("api/items", false);
    
            if (response.IsSuccess)
            {
                var results = new ObservableCollection<HomePageResult>();
    
                foreach (Item i in response.Data)
                {
                    results.Add(new HomePageResult
                    {
                        //Assign the properties here
                    });
                }
    
                Results = results;
            }
        }
    }
    

    ```

    MainPage.cs ``` private MainPageViewModel ViewModel;

        public MainPage ()
        {
            InitializeComponent();
            ViewModel = new MainPageViewModel();
            this.BindingContext = ViewModel;
        }
    
        protected override void OnAppearing()
        {
            ViewModel.GetStuff();
        }
    

    ```

    Monday, April 16, 2018 10:25 PM

Answers

  • User248153 posted

    could you try this? Non updating UIs ar mostly because their data is not updated on the UIThread.

    Login.cs

    private async void ValidLogin()
    {
        Device.BeginInvokeOnMainThread(() =>
            {
            App.Current.MainPage = App.GetHomePage();
            await Navigation.PopToRootAsync();
            });
    }
    
    • Marked as answer by Anonymous Thursday, June 3, 2021 12:00 AM
    Tuesday, April 17, 2018 7:15 AM

All replies

  • User248153 posted

    could you try this? Non updating UIs ar mostly because their data is not updated on the UIThread.

    Login.cs

    private async void ValidLogin()
    {
        Device.BeginInvokeOnMainThread(() =>
            {
            App.Current.MainPage = App.GetHomePage();
            await Navigation.PopToRootAsync();
            });
    }
    
    • Marked as answer by Anonymous Thursday, June 3, 2021 12:00 AM
    Tuesday, April 17, 2018 7:15 AM
  • User366410 posted

    Neither of these answers worked.

    @"Mr.Pearce" The async load from login did nothing.

    @XamarinRobert - I was already using Observable collection as shown in my code. I tried resetting the ItemSource in OnAppearing() but that did not help.

    Wednesday, April 18, 2018 12:43 AM
  • User366410 posted

    Alright, so I went back and tried editing the XML. Something is wrong with the grid, because when I take that out, everything works fine. The code below only works when 1) the supplied item source is fixed from the beginning 2) the screen is rotated

    <?xml version="1.0" encoding="utf-8" ?> <ContentPage xmlns="http://xamarin.com/schemas/2014/forms" xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml" x:Class="MyApp.Views.MainPage"> <ContentPage.Content> <StackLayout> <StackLayout> <Label x:Name="NewMatchHeader" FontSize="18" TextColor="Black" FontAttributes="Bold" Text="{Binding MatchCount}" /> </StackLayout> <StackLayout> <ListView x:Name="NewMatchesView" Margin="0,15,0,0" VerticalOptions="FillAndExpand" ItemsSource="{Binding Results}" RowHeight="140"
    SeparatorColor="#CCCCCC" BackgroundColor="#FFFFFF"> <ListView.ItemTemplate> <DataTemplate> <ViewCell> <Grid RowSpacing="0" Margin="0,10,0,0" > <Grid.RowDefinitions> <RowDefinition Height="Auto" /> <RowDefinition Height="Auto" /> <RowDefinition Height="Auto" /> <RowDefinition Height="Auto" /> <RowDefinition Height="Auto" /> <RowDefinition Height="Auto" /> </Grid.RowDefinitions> <Grid.ColumnDefinitions> <ColumnDefinition Width="80" /> <ColumnDefinition Width="*" /> </Grid.ColumnDefinitions> <Label Text="{Binding score}" FontSize="32" FontAttributes="Bold" TextColor="{StaticResource highlightColor}" Grid.Column="1" Grid.Row="0"/> <Label Text="{Binding title}" TextColor="#999999" Grid.Column="1" Grid.Row="1" FontSize="14" /> <Label Text="{Binding name}" TextColor="Black" Grid.Column="1" Grid.Row="2" FontSize="20" FontAttributes="Bold"/> <BoxView HeightRequest="1" Color="#EEEEEE" Grid.Column="1" Grid.Row="3" Margin="0,3,0,3"/> <Label Text="{Binding profile}" TextColor="#999999" Grid.Column="1" Grid.Row="4" FontSize="12"/> <Label Text="{Binding description}" TextColor="#999999" Grid.Column="1" Grid.Row="5" FontSize="12"/> </Grid> </ViewCell> </DataTemplate> </ListView.ItemTemplate> </ListView> </StackLayout> </StackLayout> </ContentPage.Content> </ContentPage>

    Wednesday, April 18, 2018 1:24 AM
  • User384560 posted

    Did you figure this out? I have the same issue with subsequent bindings not working on labels...I take the properties out of the grid and the bindings work fine. FYI I'm not using a Listview.

    Saturday, September 28, 2019 12:43 PM