c# - 当我单击 GridView 项时返回 ImageView 实例

标签 c# android xamarin.android mvvmcross

当我点击GridView项时如何返回ImageView实例?

我为 ItemClick 创建自定义绑定(bind)事件:

public class ItemClickSquareBinding
        : MvxBaseAndroidTargetBinding
    {
        private readonly GridView _gridView;
        private IMvxCommand _command;

        public ItemClickSquareBinding(GridView gridView)
        {
            _gridView = gridView;
            _gridView.ItemClick += GridView_ItemClick;
        }

        private void GridView_ItemClick(object sender, AdapterView.ItemClickEventArgs e)
        {
            //----->Get ImageView
        }

        public override void SetValue(object value)
        {
            _command = (IMvxCommand)value;
        }

        protected override void Dispose(bool isDisposing)
        {
            if (isDisposing)
            {
                _gridView.ItemClick -= GridView_ItemClick;
            }
            base.Dispose(isDisposing);
        }

        public override Type TargetType
        {
            get { return typeof(IMvxCommand); }
        }

        public override MvxBindingMode DefaultMode
        {
            get { return MvxBindingMode.OneWay; }
        }
    }

我的 GridView:

<cirrious.mvvmcross.binding.android.views.MvxBindableGridView
        android:layout_width="fill_parent"
        android:layout_height="fill_parent"
        android:numColumns="4"
        android:gravity="center"
        android:listSelector="#00000000"
        local:MvxItemTemplate="@layout/itemimage"
        local:MvxBind="{'ItemsSource':{'Path':'Squares'}, 'ClickItemSquare':{'Path':'ClickCommand'}}" />

我的 ImageView :

<ImageView
      xmlns:android="http://schemas.android.com/apk/res/android"
      xmlns:local="http://schemas.android.com/apk/res/LeSommet.ZooSnap.UI.Android"
      android:layout_width="80dp"
      android:layout_height="80dp"
      android:padding="5dp"
      android:layout_gravity="center"
      local:MvxBind="{'ResourcesImagePath':{'Path':'ImagePath'}}"
  />

当我点击GridView项时如何返回ImageView实例? (或者我如何返回点击我的对象实例)

最佳答案

下面三个答案...我更喜欢标记为3的答案

1)更简单的方法

在非常基本的层面上,我认为您可以使用内置绑定(bind)来实现此目的。

查看ItemClickhttps://github.com/slodge/MvvmCross/blob/vnext/Cirrious/Cirrious.MvvmCross.Binding.Droid/Views/MvxBindableGridView.cs你应该能够这样做:

<cirrious.mvvmcross.binding.android.views.MvxBindableGridView
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:numColumns="4"
    android:gravity="center"
    android:listSelector="#00000000"
    local:MvxItemTemplate="@layout/itemimage"
    local:MvxBind="{'ItemsSource':{'Path':'Squares'}, 'ItemClick':{'Path':'ClickCommand'}}" />

哪里ClickCommand是这样的:

public ICommand ClickCommand { get { return new MvxRelayCommand<Square>(square => square.Foo()); } }

如果这不起作用,请raise a bug with test code - 网格是社区捐赠给 MvvmCross 的,所以我还没有使用过。


2) 让您的自定义绑定(bind)发挥作用

如果您确实想要进行自定义绑定(bind)。

使用 Intellisense,它看起来像 AdapterView.ItemClickEventArgs有几个潜在有用的属性:

        e.View;
        e.Position;

这样您就可以访问View如果你想 - 然后可以使用类似 FindViewById<> 的东西查找包含的 View 。

或者您可以访问Position然后可以: - 使用适配器方法,如 public override Object GetItem(int position)从原始数组中获取 Java 包装的对象 - 或者可以直接在传入数组或可枚举上使用访问器方法。


3)我通常的工作方式

当我只想单击列表项或列表项的一部分时,我通常不会执行此类自定义绑定(bind)。

相反,我编写 ViewModel,以便它们公开启用行为的集合 - 我尝试呈现模型对象的启用行为的包装器,而不是模型对象本身。

在这种方法中,ViewModel 公开了 List<WrappedSquare>而不是List<Square>

public WrappedSquare
{
   Square _saure;
   SquareViewModel _square;

   public WrappedSquare(Square square, SquareViewModel parent)
   {
       /* assignment */
   }

   public ICommand TheCommand { get { return MvxRelayCommand(() -> _parent.DoStuff(_square)); } }

   public Square TheSquare { get { return _square; } } 
}

列表项中的 axml 具有如下绑定(bind):

<ImageView
      xmlns:android="http://schemas.android.com/apk/res/android"
      xmlns:local="http://schemas.android.com/apk/res/LeSommet.ZooSnap.UI.Android"
      android:layout_width="80dp"
      android:layout_height="80dp"
      android:padding="5dp"
      android:layout_gravity="center"
      local:MvxBind="{'ResourcesImagePath':{'Path':'TheSquare.ImagePath'},'Click':{'Path':'TheCommand'}}"
  />

网格的 axml 是:

<cirrious.mvvmcross.binding.android.views.MvxBindableGridView
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:numColumns="4"
    android:gravity="center"
    android:listSelector="#00000000"
    local:MvxItemTemplate="@layout/itemimage"
    local:MvxBind="{'ItemsSource':{'Path':'WrappedSquares'}}" />

此示例代码改编自MVVMCross changing ViewModel within a MvxBindableListView - 那里的答案也与这个问题相关。


这种方法的一个真实示例是 session 示例,它使用 WithCommand<T>启用从列表到详细 View 的导航。

但是...此方法有一个警告 - 请注意,在使用 WithCommand<T> 时我们在 iOS/MonoTouch 中发现了内存泄漏 - 基本上 GarbageCollection 拒绝收集嵌入的 MvxRelayCommand - 这就是为什么WithCommand<T>IDisposable为什么BaseSessionListViewMode清除列表并处理 WithCommand View 分离时的元素。

关于c# - 当我单击 GridView 项时返回 ImageView 实例,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13146942/

相关文章:

c# - 调用构造函数的顺序

android - Genymotion 拒绝以 "The Genymotion virtual device could not get an IP address."开头

c# - 关闭\销毁异步方法中的 Activity

xamarin.forms - Httpclient Xamarin Forms 调用在 Android 中不起作用

c# - 我应该在 C# 应用程序中存储 WIA 设备还是只存储 WIA 设备 ID?

c# - 尝试为 IDE 的进程内编译器设置 "References"参数时出现问题

java - 布局 - 图像不在底部且重叠

android - 在 Android 应用中使用 ChromeView

c# - 无效的资源目录名称: “res animation” aapt.exe

c# - 如何在微软新的Visual Studio Code中编译c#?