【问题标题】:How to get access the element in code behind, which is declared inside a DataTemplate in xaml page in Xamarin.Foms?如何访问后面代码中的元素,该元素在 Xamarin.Foms 的 xaml 页面中的 DataTemplate 中声明?
【发布时间】:2019-04-02 06:10:13
【问题描述】:

我正在尝试通过单击按钮访问在 DataTemplate 中声明的条目,该条目实际上位于 ListView 的 ItemTemplate 中。

<StackLayout>

    <Button Text="GetEntryTemplate" Clicked="Button_Clicked"/>

    <ListView x:Name="listView" ItemsSource="{Binding Customer}">

        <ListView.ItemTemplate>

            <DataTemplate>

                <ViewCell>

                    <Entry Text="Xamarin"/>

                </ViewCell>

            </DataTemplate>

        </ListView.ItemTemplate>

    </ListView>

</StackLayout>


    private void Button_Clicked(object sender, EventArgs e)
    {
        var loadedTemplate = listView.ItemTemplate.CreateContent();
        var view = ((loadedTemplate as ViewCell).View as Entry).Text;            
    }

我试过 CreateContent(),它实际上并没有显示运行时的变化。

谁能帮我解决这个问题。简而言之,我需要通过按钮单击访问现有条目实例(在 DataTemplate 中声明)文本。

【问题讨论】:

  • 我认为通过谷歌搜索你可以找到解决方案。根据我对 Windows 窗体的经验,这样的东西应该可以工作 - forums.xamarin.com/discussion/129774/… 但似乎在 Xamarin 的上下文中还有其他方法可能更好。
  • 对我来说这听起来像是XY-Problem。你需要这个做什么?当然,运行时更改不会反映,因为您正在创建模板的 new 实例,而不是访问现有实例。
  • 列表视图具有视图单元格的集合。那么您到底想引用哪个条目:第一个、选择的、用户录制的?
  • 嗨@Arvis,我的收藏中只有一件物品。所以我有一个条目。我需要从后面的代码中访问这个条目文本。

标签: c# xaml xamarin.forms


【解决方案1】:

您可以使用Data-Binding来设置和获取条目的文本。

在xml中

<StackLayout>

    <Button Text="GetEntryTemplate" Clicked="Button_Clicked"/>

    <ListView x:Name="listView">

        <ListView.ItemTemplate>

            <DataTemplate>

                <ViewCell>

                    <Entry TextColor="Black" Text="{Binding Content,Mode=TwoWay}"/>

                </ViewCell>

            </DataTemplate>

        </ListView.ItemTemplate>

    </ListView>

</StackLayout>

在你的代码后面

创建一个模式(例如我的名为 Data 的模型)

public class Data
{
    public string Content { get; set; }
}

在 contentPage 中

public partial class MainPage : ContentPage
{

    public ObservableCollection<Data> MySource { get; set; }

    public MainPage()
    {
        InitializeComponent();

        BindingContext = this;



        MySource = new ObservableCollection<Data>()
        {
          new Data() {Content="Entry_1" },
        };

        listView.ItemsSource = MySource;

    }



    private void Button_Clicked(object sender, EventArgs e)
    {

        DisplayAlert("title", MySource[0].Content, "cancel");

    }
}

【讨论】:

    【解决方案2】:

    我认为,你必须选择另一种方法。

    为什么不将Binding 用于ListView 中的Entry?如果您是 Xamarin 新手,我建议您阅读 MVVM 模式:link to MVVM

    您可以在 Customer 类中添加类似 EntryText 的参数,并从您的 ViewModel 中获取值,您将在其中创建绑定参数。

    【讨论】:

      【解决方案3】:

      更好的方法是使用带有数据绑定的视图模型。

      但是如果你必须引用控制元素本身,你可以这样做 (项目来源必须在集合中至少有一项,例如在 xaml 中显式添加项目):

      <Button Text="GetEntryTemplate" Clicked="Button_OnClicked"/>
      
      <ListView x:Name="listView">
      
          <ListView.ItemsSource>
              <x:Array Type="{x:Type x:String}">
                  <x:String>my customer</x:String>
              </x:Array>
          </ListView.ItemsSource>
      
          <ListView.ItemTemplate>
              <DataTemplate>
                  <ViewCell>
                      <Entry x:Name="cellEntry" Text="Xamarin"/>
                  </ViewCell>
              </DataTemplate>
          </ListView.ItemTemplate>
      
      </ListView>
      

      后面的代码:

      private void Button_OnClicked(object sender, EventArgs e)
      {
          var cell = listView.TemplatedItems.FirstOrDefault();
          var entry = (Entry)cell.FindByName("cellEntry");
          DisplayAlert("My Entry", entry.Text, "Close");
      }
      

      【讨论】:

      • 使用DataTemplate时,在listview中设置属性name是不明智的。
      • @LucasZhang-MSFT 这不是不明智的,但更像是无效的方法,但这只是对 OP 问题的直接回答:How to access the Entry instance through the Button click?
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多