2016-07-26 5 views
0

Xamarin Forms에서 내 목록에 컨텍스트 작업을 구현하려고하는데 작동하지 않습니다. XAML을 사용하지 않고 대신 코드에서 레이아웃을 만듭니다. https://developer.xamarin.com/guides/xamarin-forms/user-interface/listview/interactivity/#Context_Actions의 단계를 따르려고하고 있으며 "편집"을 클릭하면 새 페이지를 보내려고합니다.Xamarin Forms 컨텍스트 작업 구현

제 코드를 정리하고 제 기능을 작동시키기위한 약한 시도를 제거했습니다.

그래서이 내 사용자 지정 목록 세포입니다 :

public class PickerListCell : TextCell 
{ 
    public PickerListCell() 
    { 
     var moreAction = new MenuItem { Text = App.Translate ("Edit") }; 
     moreAction.SetBinding (MenuItem.CommandParameterProperty, new Binding (".")); 
     moreAction.Clicked += async (sender, e) => { 
      var mi = ((MenuItem)sender); 
      var option = (PickerListPage.OptionListItem)mi.CommandParameter; 

      var recId = new Guid (option.Value); 

      // This is where I want to call a method declared in my page to be able to push a page to the Navigation stack 

     }; 
     ContextActions.Add (moreAction); 
    } 
} 

그리고 여기 내 모델 :

public class OptionListItem 
{ 
    public string Caption { get; set; } 

    public string Value { get; set; } 
} 

그리고 이것은 페이지입니다 : 당신이에서 볼 수 있듯이

public class PickerPage : ContentPage 
{ 
    ListView listView { get; set; } 

    public PickerPage (OptionListItem [] items) 
    { 
     listView = new ListView() ; 

     Content = new StackLayout { 
      Children = { listView } 
     }; 

     var cell = new DataTemplate (typeof (PickerListCell)); 
     cell.SetBinding (PickerListCell.TextProperty, "Caption"); 
     cell.SetBinding (PickerListCell.CommandParameterProperty, "Value"); 


     listView.ItemTemplate = cell; 
     listView.ItemsSource = items; 
    } 

    // This is the method I want to activate when the context action is called 
    void OnEditAction (object sender, EventArgs e) 
    { 
     var cell = (sender as Xamarin.Forms.MenuItem).BindingContext as PickerListCell; 

     await Navigation.PushAsync (new RecordEditPage (recId), true); 
    } 

} 

코드에서 내 의견, 내가 어디에 물건이 실종 있다고 믿는 지적했다.

제발 도와주세요! 감사합니다.

답변

0

일부 게시물, 특히 https://forums.xamarin.com/discussion/27881/best-practive-mvvm-navigation-when-command-is-not-available의 도움을 받아 확인해 보니 다음 방법으로 나왔습니다.보기에는 완전히 만족하지는 않지만.

명령이 MessagingCenter을 사용하여 실행되고있을 때 내 사용자 정의 셀은 이제 발표 :

public class PickerListCell : TextCell 
{ 

    public PickerListCell() 
    { 
     var moreAction = new MenuItem { Text = App.Translate ("Edit") }; 
     moreAction.SetBinding (MenuItem.CommandParameterProperty, new Binding (".")); 
     moreAction.Clicked += async (sender, e) => { 
      var mi = ((MenuItem)sender); 
      var option = (PickerListPage.OptionListItem)mi.CommandParameter; 

      var recId = new Guid (option.Value); 

      // HERE I send a request to open a new page. This looks a 
      // bit crappy with a magic string. It will be replaced with a constant or enum 
      MessagingCenter.Send<OptionListItem, Guid> (this, "PushPage", recId); 
     }; 
     ContextActions.Add (moreAction); 
    } 
} 

그리고 메시징 서비스에이 구독을 추가 내 PickerPage 생성자

가 :

MessagingCenter.Subscribe<OptionListItem, Guid> (this, "PushPage", (sender, recId) => { 
      Navigation.PushAsync (new RecordEditPage (recId), true); 
     }); 

모든이 그냥 작동 찾는다. 그러나 그것이 의도 된 방식인지 확실하지 않다. 바인딩이 메시징 서비스없이이 문제를 해결할 수 있어야한다고 생각하지만 페이지의 메소드에 바인딩하는 방법, 모델에만 바인딩하는 방법을 찾을 수 없으며 메소드로 내 모델을 오염시키고 싶지 않습니다. 이들은 XF에 의존합니다.

1

아마도 너에게 너무 늦었지만 다른 사람들을 도울 수 있습니다. 내가 이것을 찾은 방법은 ViewCell을 생성 할 때 페이지의 인스턴스를 전달하는 것입니다.

public class PickerListCell : TextCell 
{ 
    public PickerListCell (PickerPage myPage) 
    { 
     var moreAction = new MenuItem { Text = App.Translate ("Edit") }; 
     moreAction.SetBinding (MenuItem.CommandParameterProperty, new Binding (".")); 
     moreAction.Clicked += async (sender, e) => { 
      var mi = ((MenuItem)sender); 
      var option = (PickerListPage.OptionListItem)mi.CommandParameter; 

      var recId = new Guid (option.Value); 

      myPage.OnEditAction(); 

     }; 
     ContextActions.Add (moreAction); 
    } 
} 

그래서, 당신의 페이지 :

public class PickerPage : ContentPage 
{ 
    ListView listView { get; set; } 

    public PickerPage (OptionListItem [] items) 
    { 
     listView = new ListView() ; 

     Content = new StackLayout { 
      Children = { listView } 
     }; 

     var cell = new DataTemplate(() => {return new PickerListCell(this); });    
     cell.SetBinding (PickerListCell.TextProperty, "Caption"); 
     cell.SetBinding (PickerListCell.CommandParameterProperty, "Value"); 


     listView.ItemTemplate = cell; 
     listView.ItemsSource = items; 
    } 


    void OnEditAction (object sender, EventArgs e) 
    { 
     var cell = (sender as Xamarin.Forms.MenuItem).BindingContext as PickerListCell; 

     await Navigation.PushAsync (new RecordEditPage (recId), true); 
    } 

}