简体   繁体   English

在C#中的Android活动之间传递自定义对象

[英]Passing custom object between Android activities in C#

I am creating an android app in VS2012 using Xamarin.Android. 我正在使用Xamarin.Android在VS2012中创建一个android应用。 I am displaying a custom list in Main screen. 我在主屏幕上显示一个自定义列表。 I need to pass a custom object(with ID,String,String,String properties) from this Main activity to another when user clicks on list item. 当用户单击列表项时,我需要将此主要活动的自定义对象(具有ID,String,String,String属性)传递给另一个。

Can anyone please help me with some example? 有人可以帮我举些例子吗?

edit: 编辑:

I have already tried solution mention in other question 我已经尝试过其他问题的解决方案提及

but the problem is I am getting below exception: 但问题是我得到以下异常:

This is how I am extracting in second activity 这是我在第二项活动中提取的方式

InsuranceReminderBO i = (InsuranceReminderBO)Intent.GetSerializableExtra("SelectedItemID");

i is null 我为空

and in first activity setting it like this: 第一个活动中将其设置为:

Intent intent = new Intent(this, typeof(ReminderDetails));

intent.PutExtra("SelectedItemID", selectedInsurance);

StartActivity(typeof(ReminderDetails));

where class InsuranceReminderBO is defined as 其中class InsuranceReminderBO定义为

public class InsuranceReminderBO : Java.Lang.Object, Java.IO.ISerializable

I have also tried using IParcelable but in that I got error Creator is not defined in ICreator or Creator 我也尝试使用IParcelable但由于出现错误Creator is not defined in ICreator or Creator

Following the implementation of Iparcelable on CustomObject 在CustomObject上实现Iparcelable之后

'public class InsuranceReminderBO : Java.Lang.Object, IParcelable
    {
        public InsuranceReminderBO()
        {
        }

        #region Objects and Properties
        private int id;
        private String strCompanyName;
        private String strPremiumAmount;
        private String stDueDate;

        public int ID
        {
            get { return this.id; }
            set { this.id = value; }
        }

        public String Company_Name
        {
            get { return this.strCompanyName; }
            set { this.strCompanyName = value; }
        }

        public String Premium_Amount
        {
            get { return this.strPremiumAmount; }
            set { this.strPremiumAmount = value; }
        }

        public String Due_Date
        {
            get { return this.stDueDate; }
            set { this.stDueDate = value; }
        }
        #endregion

        #region IParcelable implementation

        // The creator creates an instance of the specified object
        private static readonly GenericParcelableCreator<InsuranceReminderBO> _creator 
            = new GenericParcelableCreator<InsuranceReminderBO>((parcel) => new InsuranceReminderBO(parcel));

        [ExportField("CREATOR")]
        public static GenericParcelableCreator<InsuranceReminderBO> GetCreator()
        {
            return _creator;
        }

        // Create a new SelectListItem populated with the values in parcel
        private InsuranceReminderBO(Parcel parcel)
        {
            ID = parcel.ReadInt();
            Company_Name = parcel.ReadString();
            Premium_Amount = parcel.ReadString();
            Due_Date = parcel.ReadString();
        }

        public int DescribeContents()
        {
            return 0;
        }

        // Save this instance's values to the parcel
        public void WriteToParcel(Parcel dest, ParcelableWriteFlags flags)
        {
            dest.WriteInt(ID);
            dest.WriteString(Company_Name);
            dest.WriteString(Premium_Amount);
            dest.WriteString(Due_Date);
        }

        // Closest to the 'Java' way of implementing the creator
        /*public sealed class SelectListItemCreator : Java.Lang.Object, IParcelableCreator
        {
            public Java.Lang.Object CreateFromParcel(Parcel source)
            {
                return new SelectListItem(source);
            }

            public Java.Lang.Object[] NewArray(int size)
            {
                return new SelectListItem[size];
            }
        }*/

        #endregion
    }

#region GenericParcelableCreator
    /// <summary>
    /// Generic Parcelable creator that can be used to create objects from parcels
    /// </summary>
    public sealed class GenericParcelableCreator<T> : Java.Lang.Object, IParcelableCreator
        where T : Java.Lang.Object, new()
    {
        private readonly Func<Parcel, T> _createFunc;

        /// <summary>
        /// Initializes a new instance of the <see cref="ParcelableDemo.GenericParcelableCreator`1"/> class.
        /// </summary>
        /// <param name='createFromParcelFunc'>
        /// Func that creates an instance of T, populated with the values from the parcel parameter
        /// </param>
        public GenericParcelableCreator(Func<Parcel, T> createFromParcelFunc)
        {
            _createFunc = createFromParcelFunc;
        }

        #region IParcelableCreator Implementation

        public Java.Lang.Object CreateFromParcel(Parcel source)
        {
            return _createFunc(source);
        }

        public Java.Lang.Object[] NewArray(int size)
        {
            return new T[size];
        }
        #endregion
    }
#endregion'

I am putting object in intent as 我将目的放在意为

InsuranceReminderBO selectedInsurance = listOfInsurance[e.Position];
Intent intent = new Intent(this, typeof(ReminderDetails));
            intent.PutExtra("SelectedItem", selectedInsurance);

And reading in second activity as 在第二个活动中阅读为

InsuranceReminderBO i = (InsuranceReminderBO)Intent.GetParcelableExtra("SelectedItem");

but getting i as null. 但让我为空。

To coat tail on the servicestack.text solution, you can just download the android DLL's and reference them into your solution. 要在servicestack.text解决方案上添加尾巴,您只需下载android DLL并将其引用到您的解决方案中即可。 You can use this and add it to your solution, build it separately, as alternatives. 您可以使用它并将其添加到解决方案中,作为替代方案单独构建。 https://github.com/ServiceStack/ServiceStack.Text/tree/master/src/ServiceStack.Text.Android https://github.com/ServiceStack/ServiceStack.Text/tree/master/src/ServiceStack.Text.Android

Also I use a couple of methods to convert items back and forth that may be helpful, try 另外,我使用了几种方法来回转换项目,这可能会有所帮助,请尝试

static public string ToJSON(this object item)
{
  var myval = JsonSerializer.SerializeToString(item);
  return myval;
}
static public T FromJSON<T>(string code)
{
   var item = JsonSerializer.DeserializeFromString<T>(code);
   return item;
}

There's an article on using IParcelable in Xamarin here . 有一个关于在Xamarin使用IParcelable的文章在这里

Personally, I've always just serialised to JSON, passed a string extra and deserialised it on the other end. 就个人而言,我一直只是序列化为JSON,额外传递了一个字符串,然后在另一端反序列化了它。

If you're using ServiceStack.Text , which I like, you can do something like this: 如果您使用的是我喜欢的ServiceStack.Text ,则可以执行以下操作:

intent.PutExtra("SelectedItemId", JsonSerializer.SerializeToString(selectedInsurance));

And on the other end: 在另一端:

var insurance = JsonSerializer.DeserializeFromString<InsuranceReminderBO>(Intent.GetStringExtra("SelectedItemId"))

No need to implement Java.Lang.Object, Java.IO.ISerializable 无需实现Java.Lang.Object, Java.IO.ISerializable

After doing a lot of search on Google finally i found a solution here . 在Google上进行了大量搜索之后,我终于在这里找到了解决方案。

Basically I used StartActivity(intent); 基本上我使用StartActivity(intent);

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM