2017-05-06 2 views
1

xamarin 양식 IOS를 사용하는 바인딩에 몇 가지 문제가 있습니다. 바인딩이 있습니다 첫 페이지가 나타나면 화면 가운데에로드 레이블이 표시됩니다.Xamarin Forms IOS의 바인딩 문제 및 OnAppearing 문제

후 목록보기에서 데이터를로드하면 바인딩을 통해로드 레이블이 숨겨지고 목록보기가 표시됩니다. 나는이 REPO Xamarin forms IOS Android Test

그것은 잘 작동에있는 안드로이드 프로젝트에서

. repro 프로젝트의 ios에서는 응용 프로그램이 처음로드 될 때로드 레이블이 숨겨지고 화면을 탭하면 표시됩니다. 계속하면로드 레이블이 사라지고 빈 화면이 표시되지만 화면을 다시 누르면 목록 데이터보기가 나타납니다.

나는 이것이 xamarin의 버그라고 생각하지만 바인딩이 올바르지 않기를 바라고 있습니다. 이 문제가 해결 될 수 있도록 노력하겠습니다. 또 다른 두 가지 문제가 있습니다. 목록보기 항목을 클릭하고 뒤로 이동하면 켜짐 표시가 나타나지 않으므로 데이터가 새로 고쳐지지 않습니다.

안드로이드에서는 문제없이 실행됩니다. 위에서 언급 한 단계와 같이 화면을 탭하면 가끔씩 나타나는 경우가 있습니다. 마지막 문제는 IOS 사이의 전환이 나타나면 트리거되지 않는다는 것입니다. 안드로이드가 있습니다. 이 문제에 대한 도움을 주시면 감사하겠습니다. 나는이 문제에 대한 해결책을 광범위하게 찾고 아직 찾지도 대답도하지 않았다. 감사합니다.

다음은 유용한 일부 코드 단편입니다. 이 코드는 테스트하려는 경우 GitHub 레포에도 있습니다. 내가 속성을 통지 사용하고 XAML

<Label x:Name="xEmptyListView" 
     FontSize="16" 
     HorizontalOptions="CenterAndExpand" 
     HorizontalTextAlignment="Center" 
     VerticalOptions="CenterAndExpand"    
     Text="{Binding ListViewVisibleText, Mode=TwoWay}" 
     IsVisible="{Binding IsListViewLabelEmptyVisible, Mode=TwoWay }"/> 

    <ListView x:Name="ItemsListView" 
      ItemsSource="{Binding Items}" 
      VerticalOptions="FillAndExpand" 
      HasUnevenRows="true" 
      RefreshCommand="{Binding LoadItemsCommand}" 
      IsPullToRefreshEnabled="true" 
      IsRefreshing="{Binding IsBusy, Mode=OneWay}" 
      CachingStrategy="RecycleElement" 
      ItemSelected="OnItemSelected" 
      IsVisible="{Binding IsListViewVisible, Mode=TwoWay}" 
      IsEnabled="{Binding IsActivityRunning, Mode=TwoWay, Converter={StaticResource InverseBooleanConverter}}"> 

뷰 모델에서

private bool activityRunning { get; set; } 

    public bool IsActivityRunning 
    { 
     get { return activityRunning; } 
     set 
     { 
      if (activityRunning == value) 
       return; 

      activityRunning = value; 
      OnPropertyChanged("IsActivityRunning"); 
     } 
    } 

    private string listViewVisibleText { get; set; } 
    public string ListViewVisibleText 
    { 
     get { return listViewVisibleText; } 
     set 
     { 
      if (listViewVisibleText == value) 
       return; 

      listViewVisibleText = value; 
      OnPropertyChanged("ListViewVisibleText"); 
     } 
    } 



    private bool listViewLabelEmptyVisible { get; set; } 

    public bool IsListViewLabelEmptyVisible 
    { 
     get 
     { 
      if (Items == null || Items.Count == 0) 
      { 
       if (IsBusy) 
       { 
        ListViewVisibleText = "Loading..."; 
       } 
       else 
       { 

        ListViewVisibleText = "No Items found"; 


       } 
       listViewLabelEmptyVisible = true; 
      } 
      else 
      { 
       ListViewVisibleText = string.Empty; 
       listViewLabelEmptyVisible = false; 
      } 

      OnPropertyChanged("IsListViewLabelEmptyVisible"); 
      return listViewLabelEmptyVisible; 
     } 
    } 

    private bool listViewVisible { get; set; } 

    public bool IsListViewVisible 
    { 
     get 
     { 
      if (Items == null || Items.Count == 0) 
      { 
       listViewVisible = false; 
      } 
      else 
      { 
       listViewVisible = true; 
      } 

      OnPropertyChanged("IsListViewVisible"); 
      return listViewVisible; 
     } 
    } 

XAML.cs

protected override void OnAppearing() 
     { 
      base.OnAppearing(); 


       viewModel.LoadItemsCommand.Execute(null); 
     } 

이 변경되었습니다. 그것은이 내 시야 모델은 notifyproperty 변경에 대한 상속 무엇 표준 코드

당신이이 프로젝트 자 마린 테스트를 만들 때 관찰 개체

public class BaseViewModel : ObservableObject 

에서 상속 기본 뷰 모델

public class ItemsViewModel : BaseViewModel 

그것이 보이는 방법. 항목 등 이에게 안드로이드의 모든 작품을로드 할 때

public class ObservableObject : INotifyPropertyChanged 
    { 
     /// <summary> 
     /// Sets the property. 
     /// </summary> 
     /// <returns><c>true</c>, if property was set, <c>false</c> otherwise.</returns> 
     /// <param name="backingStore">Backing store.</param> 
     /// <param name="value">Value.</param> 
     /// <param name="propertyName">Property name.</param> 
     /// <param name="onChanged">On changed.</param> 
     /// <typeparam name="T">The 1st type parameter.</typeparam> 
     protected bool SetProperty<T>(
      ref T backingStore, T value, 
      [CallerMemberName]string propertyName = "", 
      Action onChanged = null) 
     { 
      if (EqualityComparer<T>.Default.Equals(backingStore, value)) 
       return false; 

      backingStore = value; 
      onChanged?.Invoke(); 
      OnPropertyChanged(propertyName); 
      return true; 
     } 

     /// <summary> 
     /// Occurs when property changed. 
     /// </summary> 
     public event PropertyChangedEventHandler PropertyChanged; 

     /// <summary> 
     /// Raises the property changed event. 
     /// </summary> 
     /// <param name="propertyName">Property name.</param> 
     protected void OnPropertyChanged([CallerMemberName]string propertyName = "") 
     { 
      var changed = PropertyChanged; 
      if (changed == null) 
       return; 

      changed.Invoke(this, new PropertyChangedEventArgs(propertyName)); 
     } 
    } 
} 

활동 실행이 설정됩니다. IOS는 그렇지 않습니다.

+0

몇 가지 예제 코드를 추가 할 수 있습니까? – Mike

답변

0

나는 이것을 알아 낸 것입니다.레이블을 표시하고 목록보기를 숨기거나 그 반대로 숨김을 처리하는 방식은 IOS가 요청을 처리하는 방식을 방해합니다. 바인딩을 제거하고 목록보기에서 속성이 변경된 핸들러를 사용하여 컨트롤을 직접 설정합니다. 탭, 뒤로 버튼 등에 나타나는 문제를 수정했습니다.

관련 문제