Comment passer un objet D'une activité à une autre sur Android

j'essaie de travailler sur l'envoi d'un objet de mon client classe d'un Activity et l'afficher dans un autre Activity .

le code de La classe de la clientèle:

public class Customer {

    private String firstName, lastName, Address;
    int Age;

    public Customer(String fname, String lname, int age, String address) {

        firstName = fname;
        lastName = lname;
        Age = age;
        Address = address;
    }

    public String printValues() {

        String data = null;

        data = "First Name :" + firstName + " Last Name :" + lastName
        + " Age : " + Age + " Address : " + Address;

        return data;
    }
}

je veux envoyer son objet d'un Activity à un autre et ensuite afficher les données sur l'autre Activity .

Comment puis-je y arriver?

629
demandé sur Swati Garg 2010-04-29 14:06:52

30 réponses

une option pourrait être de laisser votre classe personnalisée implémenter l'interface Serializable et ensuite vous pouvez passer des instances d'objet dans l'intention extra en utilisant la variante putExtra(Serializable..) de la méthode Intent#putExtra() .

Pseudo-code :

//To pass:
intent.putExtra("MyClass", obj);

// To retrieve object in second Activity
getIntent().getSerializableExtra("MyClass");

Note: assurez-vous que chaque classe imbriquée de votre classe personnalisée principale a mis en œuvre une interface sérialisable pour éviter toute exception de sérialisation. Par exemple:

class MainClass implements Serializable {

    public MainClass() {}

    public static class ChildClass implements Serializable {

        public ChildClass() {}
    }
}
741
répondu Samuh 2018-05-26 12:35:03

implémenter votre classe avec Serialisable. Supposons qu'il s'agisse de votre classe d'entités:

import java.io.Serializable;

@SuppressWarnings("serial") //With this annotation we are going to hide compiler warnings
public class Deneme implements Serializable {

    public Deneme(double id, String name) {
        this.id = id;
        this.name = name;
    }

    public double getId() {
        return id;
    }

    public void setId(double id) {
        this.id = id;
    }

    public String getName() {
        return this.name;
    }

    public void setName(String name) {
        this.name = name;
    }

    private double id;
    private String name;
}

nous envoyons l'objet appelé dene de x activity à Y activity. Quelque part dans X de l'activité;

Deneme dene = new Deneme(4,"Mustafa");
Intent i = new Intent(this, Y.class);
i.putExtra("sampleObject", dene);
startActivity(i);

dans L'activité Y, nous obtenons l'objet.

Intent i = getIntent();
Deneme dene = (Deneme)i.getSerializableExtra("sampleObject");

C'est ça.

266
répondu Mustafa Güven 2015-11-22 13:20:06
  • global variables statiques n'est pas bon génie logiciel "151930920 pratique".
  • Convertir les champs d'un objet en champs primitifs les types de données peuvent être un travail mouvementé .
  • utiliser sérialisable est OK, mais ce n'est pas la performance-efficace sur la plate-forme Android.
  • Partecelable is specifically conçu pour Android et vous devez l'utiliser. Voici un exemple simple: passer des objets personnalisés entre les activités Android

vous pouvez générer du code séparable pour votre classe en utilisant ce site .

106
répondu SohailAziz 2017-11-16 06:21:34

tout en appelant une activité

Intent intent = new Intent(fromClass.this,toClass.class).putExtra("myCustomerObj",customerObj);

dans toClass.java recevoir l'activité par

Customer customerObjInToClass = getIntent().getExtras().getParcelable("myCustomerObj");

s'il vous Plaît assurez-vous que la clientèle de la classe implémente parcelable

public class Customer implements Parcelable {

    private String firstName, lastName, address;
    int age;

    /* all your getter and setter methods */

    public Customer(Parcel in ) {
        readFromParcel( in );
    }

    public static final Parcelable.Creator CREATOR = new Parcelable.Creator() {
        public LeadData createFromParcel(Parcel in ) {
            return new Customer( in );
        }

        public Customer[] newArray(int size) {
            return new Customer[size];
        }
    };


    @Override
    public void writeToParcel(Parcel dest, int flags) {

        dest.writeString(firstName);
        dest.writeString(lastName);
        dest.writeString(address);
        dest.writeInt(age);
    }

    private void readFromParcel(Parcel in ) {

        firstName = in .readString();
        lastName  = in .readString();
        address   = in .readString();
        age       = in .readInt();
    }
86
répondu Ads 2016-07-08 20:39:33

d'après mon expérience, il y a trois solutions principales, chacune avec ses inconvénients et ses avantages:

  1. La Mise En Œuvre De Parcelable

  2. La Mise En Œuvre De Serializable

  3. utilisant une bibliothèque d'événements légère d'une sorte (par exemple, EventBus de Greenrobot ou Otto de Square)

séparable - rapide et Android standard, mais il a beaucoup de code boilerplate et nécessite des chaînes codées dur pour référence lors de tirer des valeurs sur l'intention (non fortement dactylographié).

sérialisable - près de zéro boilerplate, mais c'est l'approche la plus lente et nécessite également des chaînes codées dur lors de la traction valeurs sur l'intention (non fortement dactylographié).

Event Bus - boilerplate zéro, approche la plus rapide, et ne nécessite pas de chaînes à code dur, mais il nécessite une dépendance supplémentaire (bien que généralement léger, ~40 KB)

j'ai réalisé une comparaison détaillée autour de ces trois approches, y compris l'efficacité des repères.

77
répondu Steven Mark Ford 2018-08-11 08:09:57

utilisez gson pour convertir votre objet en JSON et passer par l'intention. Dans la nouvelle activité convertissez le JSON en objet.

dans votre build.gradle , ajoutez ceci à vos dépendances

implementation 'com.google.code.gson:gson:2.8.4'

dans votre activité, convertissez l'objet en JSON-string:

Gson gson = new Gson();
String myJson = gson.toJson(vp);
intent.putExtra("myjson", myjson);

dans votre activité de réception, convertissez la chaîne json en objet original:

Gson gson = new Gson();
YourObject ob = gson.fromJson(getIntent().getStringExtra("myjson"), YourObject.class);

Pour Kotlin c'est tout à fait le même

passer les données

val gson = Gson()
val intent = Intent(this, YourActivity::class.java)
intent.putExtra("identifier", gson.toJson(your_object))
startActivity(intent)

recevoir les données

val gson = Gson()
val yourObject = gson.fromJson<YourObject>(intent.getStringExtra("identifier"), YourObject::class.java)
64
répondu khalid 2018-10-03 09:27:35

vous pouvez aussi écrire les données de l'objet dans des chaînes temporaires et des entrées, et les passer à l'activité. Bien sûr, de cette façon, vous obtenez les données transportées, mais pas de l'objet lui-même.

mais si vous voulez juste les afficher, et ne pas utiliser l'objet dans une autre méthode ou quelque chose comme ça, cela devrait être suffisant. J'ai fait de la même façon à afficher uniquement les données d'un objet dans une autre activité.

String fName_temp   = yourObject.getFname();
String lName_temp   = yourObject.getLname();
String age_temp     = yourObject.getAge();
String address_temp = yourObject.getAddress();

Intent i = new Intent(this, ToClass.class);
i.putExtra("fname", fName_temp);
i.putExtra("lname", lName_temp);
i.putExtra("age", age_temp);
i.putExtra("address", address_temp);

startActivity(i);

vous pouvez aussi les passer directement au lieu des Templiers, mais de cette façon, c'est plus clair, à mon avis. De plus, vous pouvez régler les temp ivars à null pour qu'ils soient nettoyés par le collecteur GarbageCollector plus tôt.

bonne chance!

sur une note latérale: outrepassez toString() au lieu d'écrire votre propre méthode d'impression.

comme mentionné dans les commentaires ci-dessous, voici comment vous obtenez vos données dans une autre activité:

String fName = getIntent().getExtras().getInt("fname");
37
répondu MJB 2015-11-22 13:13:56

j'ai trouvé une méthode simple et élégante:

  • NO Parcellable
  • NON Sérialisable
  • PAS de Champ Statique
  • Aucun Événement De Bus

Méthode 1

Code de la première activité:

    final Object objSent = new Object();
    final Bundle bundle = new Bundle();
    bundle.putBinder("object_value", new ObjectWrapperForBinder(objSent));
    startActivity(new Intent(this, SecondActivity.class).putExtras(bundle));        
    Log.d(TAG, "original object=" + objSent);

Code pour la deuxième activité:

    final Object objReceived = ((ObjectWrapperForBinder)getIntent().getExtras().getBinder("object_value")).getData();
    Log.d(TAG, "received object=" + objReceived);

vous trouverez objSent et objReceived ont le même hashCode , donc ils sont identiques.

mais pourquoi passer un objet java de cette façon?

en fait, android binder va créer une référence JNI globale pour l'objet java et libérer cette référence JNI globale quand il n'y a pas de référence pour cet objet java. binder sauvegardera cette référence JNI globale en l'objet de Classeur.

*ATTENTION: cette méthode ne fonctionne que si les deux activités exécutées dans le même processus, autrement jeter ClassCastException au (ObjectWrapperForBinder)getIntent().getExtras ().getBinder ("object_value") *

class Objectfrapperforbinder defination

public class ObjectWrapperForBinder extends Binder {

    private final Object mData;

    public ObjectWrapperForBinder(Object data) {
        mData = data;
    }

    public Object getData() {
        return mData;
    }
}

Méthode 2

  • pour l'expéditeur,
    1. use sur mesure méthode native pour ajouter votre objet java à la table de référence globale JNI (via JNIEnv:: NewGlobalRef)
    2. mettez l'entier de retour (en fait, JNIEnv::NewGlobalRef return jobject, qui est un pointeur, nous pouvons le lancer à int en toute sécurité) à votre intention (via intention:: putExtra)
  • pour le récepteur
    1. obtenir le nombre entier à partir de l'Intention(via Intention::getInt)
    2. utiliser la méthode native personnalisée pour restaurer your java object from JNI global reference table (via JNIEnv::NewLocalRef)
    3. supprimer l'élément du tableau de référence mondial JNI(via JNIEnv:: DeleteGlobalRef),

mais la méthode 2 a un problème petit mais sérieux, si le récepteur ne parvient pas à restaurer l'objet java (par exemple, une exception se produit avant de restaurer l'objet java, ou L'activité du récepteur n'existe pas du tout), alors l'objet java deviendra orphelin ou trou de mémoire, Méthode 1 n'ont pas ce problème, parce qu'android classeur de gérer cette exception

Méthode 3

pour invoquer l'objet java à distance, nous allons créer un contrat/interface de données pour décrire l'objet java, nous allons utiliser le fichier aidl

IDataContract.aidl

package com.example.objectwrapper;
interface IDataContract {
    int func1(String arg1);
    int func2(String arg1);
}

Code pour la première activité

    final IDataContract objSent = new IDataContract.Stub() {

        @Override
        public int func2(String arg1) throws RemoteException {
            // TODO Auto-generated method stub
            Log.d(TAG, "func2:: arg1=" + arg1);
            return 102;
        }

        @Override
        public int func1(String arg1) throws RemoteException {
            // TODO Auto-generated method stub
            Log.d(TAG, "func1:: arg1=" + arg1);
            return 101;
        }
    };
    final Bundle bundle = new Bundle();
    bundle.putBinder("object_value", objSent.asBinder());
    startActivity(new Intent(this, SecondActivity.class).putExtras(bundle));
    Log.d(TAG, "original object=" + objSent);

Code pour le second activité:

changer le android:processus d'attribut dans AndroidManifest.xml à un non-vide nom du processus pour s'assurer que la deuxième activité de l'exécuter dans un autre processus

    final IDataContract objReceived = IDataContract.Stub.asInterface(getIntent().getExtras().getBinder("object_value"));
    try {
        Log.d(TAG, "received object=" + objReceived + ", func1()=" + objReceived.func1("test1") + ", func2()=" + objReceived.func2("test2"));
    } catch (RemoteException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }

de cette façon, nous pouvons passer une interface entre deux activités, même si elles s'exécutent dans un processus différent, et appeler la méthode d'interface à distance

Méthode 4

méthode 3 ne semble pas assez simple parce que nous devons mettre en place une interface aidl. Si vous voulez juste faire tâche simple et la valeur de retour de la méthode est inutile, nous pouvons utiliser android.OS.Messager

Code pour la première activité (expéditeur):

public class MainActivity extends Activity {
    private static final String TAG = "MainActivity";

    public static final int MSG_OP1 = 1;
    public static final int MSG_OP2 = 2;

    public static final String EXTRA_MESSENGER = "messenger";

    private final Handler mHandler = new Handler() {

        @Override
        public void handleMessage(Message msg) {
            // TODO Auto-generated method stub
            Log.e(TAG, "handleMessage:: msg=" + msg);
            switch (msg.what) {
            case MSG_OP1:

                break;
            case MSG_OP2:
                break;

            default:

                break;
            }
            super.handleMessage(msg);
        }

    };
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        startActivity(new Intent(this, SecondActivity.class).putExtra(EXTRA_MESSENGER, new Messenger(mHandler)));
    }
}

Code pour la deuxième activité (récepteur ):

public class SecondActivity extends Activity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_second);

        final Messenger messenger = getIntent().getParcelableExtra(MainActivity.EXTRA_MESSENGER);
        try {
            messenger.send(Message.obtain(null, MainActivity.MSG_OP1, 101, 1001, "10001"));
            messenger.send(Message.obtain(null, MainActivity.MSG_OP2, 102, 1002, "10002"));
        } catch (RemoteException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }

    }
}

tout le Messager.send s'exécute dans un gestionnaire de manière asynchrone et séquentielle.

en fait, androïde.OS.Messenger est aussi une interface aidl, si vous avez le code source android, vous pouvez trouver un fichier nommé IMessenger.aidl

package android.os;

import android.os.Message;

/** @hide */
oneway interface IMessenger {
    void send(in Message msg);
}
30
répondu Yessy 2016-08-08 02:34:49

j'ai fait une classe d'aide singleton qui contient des objets temporaires.

public class IntentHelper {

    private static IntentHelper _instance;
    private Hashtable<String, Object> _hash;

    private IntentHelper() {
        _hash = new Hashtable<String, Object>();
    }

    private static IntentHelper getInstance() {
        if(_instance==null) {
            _instance = new IntentHelper();
        }
        return _instance;
    }

    public static void addObjectForKey(Object object, String key) {
        getInstance()._hash.put(key, object);
    }

    public static Object getObjectForKey(String key) {
        IntentHelper helper = getInstance();
        Object data = helper._hash.get(key);
        helper._hash.remove(key);
        helper = null;
        return data;
    }
}

au lieu de mettre vos objets dans L'intention, utilisez IntentHelper:

IntentHelper.addObjectForKey(obj, "key");

dans votre nouvelle activité, vous pouvez obtenir l'objet:

Object obj = (Object) IntentHelper.getObjectForKey("key");

garder à l'esprit qu'une fois chargé, l'objet est supprimé pour éviter les références inutiles.

25
répondu Roger Sanoli 2012-06-21 13:04:10

il y a plusieurs façons d'accéder à des variables ou à des objets dans d'autres classes ou activités.

A. Base De Données

B. préférences partagées.

C. sérialisation des objets.

D. Une classe qui peut contenir des données communes peut être nommée comme utilitaire commun. Il dépend de vous.

E. transmission des données par Intents et par L'Interface séparable.

cela dépend sur les besoins de votre projet.

A. Base De Données

SQLite est une base de données open source qui est intégré dans Android. SQLite soutient les traits de base de données relationnelles standard comme la syntaxe de SQL, les transactions et les déclarations préparées.

tutoriels

B. préférences partagées

"

Supposons que vous souhaitez stocker le nom d'utilisateur. Donc, il y aura maintenant deux choses, une clé nom d'utilisateur, valeur valeur.

comment conserver

 // Create object of SharedPreferences.
 SharedPreferences sharedPref = PreferenceManager.getDefaultSharedPreferences(this);

 //Now get Editor
 SharedPreferences.Editor editor = sharedPref.edit();

 //Put your value
 editor.putString("userName", "stackoverlow");

 //Commits your edits
 editor.commit();

en utilisant putString(), putBoolean(), putInt(), putFloat(), et putLong() vous pouvez sauvegarder votre dtatype désiré.

Comment extraire les

SharedPreferences sharedPref = PreferenceManager.getDefaultSharedPreferences(this);
String userName = sharedPref.getString("userName", "Not Available");

http://developer.android.com/reference/android/content/SharedPreferences.html

C. sérialisation d'un Objet

Objet serlization est utilisé si l'on veux enregistrer un état de l'objet à envoyer sur un réseau ou vous pouvez l'utiliser pour votre usage.

utilisez Java beans et stocker en elle comme l'un de ses champs et d'utiliser getters et setter pour cela.

JavaBeans sont des classes Java qui ont des propriétés. Pensez propriétés comme variables d'instance privée. Depuis qu'ils sont privés, la seule façon ils peuvent être accessibles à partir de l'extérieur de leur classe est par des méthodes dans la classe. Les méthodes qui changent la valeur d'une propriété sont appelées méthodes setter, et les méthodes qui récupèrent la valeur d'une propriété sont appelées méthodes getter.

public class VariableStorage implements Serializable  {

    private String inString;

    public String getInString() {
        return inString;
    }

    public void setInString(String inString) {
        this.inString = inString;
    }
}

définissez la variable dans votre méthode de messagerie en utilisant

VariableStorage variableStorage = new VariableStorage();
variableStorage.setInString(inString);

puis utilisez la sérialisation d'objet pour sérialiser cet objet et dans votre autre classe désérialiser cet objet.

Dans la sérialisation d'un objet peut être représenté comme une séquence d'octets qui comprend les données de l'objet ainsi que des informations sur le type de l'objet et les types de données stockées dans l'objet.

Après un objet sérialisé a été écrit dans un fichier, il peut être lu à partir du fichier et désérialisé. C'est le type de l'information et de octets qui représentent l'objet et ses données peuvent être utilisées pour recréer l'objet en mémoire.

si vous voulez tutoriel pour cela se référer à:

D. CommonUtilities

vous pouvez faire une classe par vous-même qui peut contenir des données communes dont vous avez fréquemment besoin dans votre projet.

échantillon

public class CommonUtilities {

    public static String className = "CommonUtilities";

}

E. transmission de données par les intentions

S'il vous plaît se référer au tutoriel Android-Données de parcelle à passer entre Activités utilisant les classes séparables pour cette option de transmission de données.

23
répondu Nikhil Agrawal 2017-05-23 12:18:32

la meilleure façon est d'avoir une classe (appelez le contrôle) dans votre application qui tiendra une variable statique de type 'client' (dans votre cas). Initialisez la variable dans votre activité A.

par exemple:

Control.Customer = CustomerClass;

ensuite, allez à L'activité B et rapportez-la de la classe de contrôle. N'oubliez pas d'attribuer un null après avoir utilisé la variable, sinon la mémoire sera gaspillée.

15
répondu Umesh 2015-11-22 13:14:58
public class MyClass implements Serializable{
    Here is your instance variable
}

Maintenant vous voulez passer l'objet de cette classe dans startActivity. Utilisez simplement ceci:

Bundle b = new Bundle();
b.putSerializable("name", myClassObject);
intent.putExtras(b);

cela fonctionne ici parce que MyClass met en œuvre Serializable .

15
répondu Dhiral Pandya 2015-11-22 13:21:18

créez votre propre classe Customer comme suit:

import import java.io.Serializable;
public class Customer implements Serializable
{
    private String name;
    private String city;

    public Customer()
    {

    }
    public Customer(String name, String city)
    {
        this.name= name;
        this.city=city;
    }
    public String getName() 
    {
        return name;
    }
    public void setName(String name) 
    {
        this.name = name;
    }
    public String getCity() 
    {
        return city;
    }
    public void setCity(String city) 
    {
        this.city= city;
    }

}

dans votre onCreate() méthode

@Override
protected void onCreate(Bundle savedInstanceState) 
{
    super.onCreate(savedInstanceState); 
    setContentView(R.layout.activity_top);

    Customer cust=new Customer();
    cust.setName("abc");
    cust.setCity("xyz");

    Intent intent=new Intent(abc.this,xyz.class);
    intent.putExtra("bundle",cust);
    startActivity(intent); 
}

dans la classe xyz activity vous devez utiliser le code suivant:

Intent intent=getIntent();
Customer cust=(Customer)intent.getSerializableExtra("bundle");
textViewName.setText(cust.getName());
textViewCity.setText(cust.getCity());
15
répondu Mayur Chudasama 2018-07-02 14:10:42

si vous choisissez d'utiliser la façon dont Samuh décrit, rappelez-vous que seules les valeurs primitives peuvent être envoyées. Cela signifie que les valeurs qui sont parcable. Donc, si votre objet contient des objets complexes elles ne pourront pas suivre. Par exemple, les variables comme Bitmap, HashMap etc... Ces sont difficiles à passer par l'intention.

en général, je vous conseille d'envoyer seulement des types de données primitifs comme extras, comme String, int, boolean etc. Dans votre cas, ce serait: String fname , String lname , int age , et String address .

Mon avis: des objets Plus complexes sont mieux partagés par la mise en œuvre d'un ContentProvider , SDCard , etc. Il est également possible d'utiliser une variable statique , mais cela peut rapidement conduire à un code sujet à erreur...

mais encore une fois, c'est juste mon opinion subjective.

12
répondu Vidar Vestnes 2015-11-22 13:12:10

j'utilise parcelable pour envoyer des données d'une activité à une autre activité. Voici mon code qui fonctionne très bien dans mon projet.

public class Channel implements Serializable, Parcelable {

    /**  */
    private static final long serialVersionUID = 4861597073026532544L;

    private String cid;
    private String uniqueID;
    private String name;
    private String logo;
    private String thumb;


    /**
     * @return The cid
     */
    public String getCid() {
        return cid;
    }

    /**
     * @param cid
     *     The cid to set
     */
    public void setCid(String cid) {
        this.cid = cid;
    }

    /**
     * @return The uniqueID
     */
    public String getUniqueID() {
        return uniqueID;
    }

    /**
     * @param uniqueID
     *     The uniqueID to set
     */
    public void setUniqueID(String uniqueID) {
        this.uniqueID = uniqueID;
    }

    /**
     * @return The name
     */
    public String getName() {
        return name;
    }

    /**
     * @param name
     *            The name to set
     */
    public void setName(String name) {
        this.name = name;
    }

    /**
     * @return the logo
     */
    public String getLogo() {
        return logo;
    }

    /**
     * @param logo
     *     The logo to set
     */
    public void setLogo(String logo) {
        this.logo = logo;
    }

    /**
     * @return the thumb
     */
    public String getThumb() {
        return thumb;
    }

    /**
     * @param thumb
     *     The thumb to set
     */
    public void setThumb(String thumb) {
        this.thumb = thumb;
    }


    public Channel(Parcel in) {
        super();
        readFromParcel(in);
    }

    public static final Parcelable.Creator<Channel> CREATOR = new Parcelable.Creator<Channel>() {
        public Channel createFromParcel(Parcel in) {
            return new Channel(in);
        }

        public Channel[] newArray(int size) {

            return new Channel[size];
        }
    };

    public void readFromParcel(Parcel in) {
        String[] result = new String[5];
        in.readStringArray(result);

        this.cid = result[0];
        this.uniqueID = result[1];
        this.name = result[2];
        this.logo = result[3];
        this.thumb = result[4];
    }

    public int describeContents() {
        return 0;
    }

    public void writeToParcel(Parcel dest, int flags) {

        dest.writeStringArray(new String[] { this.cid, this.uniqueID,
                this.name, this.logo, this.thumb});
    }
}

en activityA utilisez-le comme ceci:

Bundle bundle = new Bundle();
bundle.putParcelableArrayList("channel",(ArrayList<Channel>) channels);
Intent intent = new Intent(ActivityA.this,ActivityB.class);
intent.putExtras(bundle);
startActivity(intent);

dans ActivityB utilisez-le comme ceci pour obtenir des données:

Bundle getBundle = this.getIntent().getExtras();
List<Channel> channelsList = getBundle.getParcelableArrayList("channel");
8
répondu Bebin T.N 2015-11-22 14:09:49

Vous pouvez essayer d'utiliser cette classe. La limitation est qu'il ne peut pas être utilisé en dehors d'un processus.

une activité:

 final Object obj1 = new Object();
 final Intent in = new Intent();
 in.putExtra(EXTRA_TEST, new Sharable(obj1));

autre activité:

final Sharable s = in.getExtras().getParcelable(EXTRA_TEST);
final Object obj2 = s.obj();

public final class Sharable implements Parcelable {

    private Object mObject;

    public static final Parcelable.Creator < Sharable > CREATOR = new Parcelable.Creator < Sharable > () {
        public Sharable createFromParcel(Parcel in ) {
            return new Sharable( in );
        }


        @Override
        public Sharable[] newArray(int size) {
            return new Sharable[size];
        }
    };

    public Sharable(final Object obj) {
        mObject = obj;
    }

    public Sharable(Parcel in ) {
        readFromParcel( in );
    }

    Object obj() {
        return mObject;
    }


    @Override
    public int describeContents() {
        return 0;
    }


    @Override
    public void writeToParcel(final Parcel out, int flags) {
        final long val = SystemClock.elapsedRealtime();
        out.writeLong(val);
        put(val, mObject);
    }

    private void readFromParcel(final Parcel in ) {
        final long val = in .readLong();
        mObject = get(val);
    }

    /////

    private static final HashMap < Long, Object > sSharableMap = new HashMap < Long, Object > (3);

    synchronized private static void put(long key, final Object obj) {
        sSharableMap.put(key, obj);
    }

    synchronized private static Object get(long key) {
        return sSharableMap.remove(key);
    }
}
7
répondu Varis 2015-11-22 13:18:38

Crète une classe comme la classe de haricots et mettre en œuvre l'interface Serializable . Ensuite, nous pouvons passer par la méthode intent , par exemple:

intent.putExtra("class", BeanClass);

puis l'obtenir de l'autre activité, par exemple:

BeanClass cb = intent.getSerializableExtra("class");
5
répondu Peter Mortensen 2015-11-22 14:29:13

créer deux méthodes dans votre classe personnalisée comme ceci

public class Qabir {

    private int age;
    private String name;

    Qabir(){
    }

    Qabir(int age,String name){
        this.age=age; this.name=name;
    }   

    // method for sending object
    public String toJSON(){
        return "{age:" + age + ",name:\"" +name +"\"}";
    }

    // method for get back original object
    public void initilizeWithJSONString(String jsonString){

        JSONObject json;        
        try {
            json =new JSONObject(jsonString );
            age=json.getInt("age");
            name=json.getString("name");
        } catch (JSONException e) {
            e.printStackTrace();
        } 
    }
}

maintenant dans votre activité d'expéditeur faites comme ceci

Qabir q= new Qabir(22,"KQ");    
Intent in=new Intent(this,SubActivity.class);
in.putExtra("obj", q.toJSON());
startActivity( in);

et dans votre activité de récepteur

Qabir q =new Qabir();
q.initilizeWithJSONString(getIntent().getStringExtra("obj"));
5
répondu Think7 2016-01-20 21:14:42

lancer une autre activité à partir de cette activité et passer les paramètres via L'objet Bundle

Intent intent = new Intent(getBaseContext(), YourActivity.class);
intent.putExtra("USER_NAME", "xyz@gmail.com");
startActivity(intent);

retrieve data on another activity (your activity)

String s = getIntent().getStringExtra("USER_NAME");

c'est ok pour le type de données simple. Mais si vous voulez transmettre des données complexes entre deux activités. U besoin de sérialiser en premier.

ici, nous avons le modèle employé

class Employee{
    private String empId;
    private int age;
    print Double salary;

    getters...
    setters...
}

vous pouvez utiliser Gson lib fourni par google pour sérialiser les données complexes comme ceci

String strEmp = new Gson().toJson(emp);
Intent intent = new Intent(getBaseContext(), YourActivity.class);
intent.putExtra("EMP", strEmp);
startActivity(intent);

Bundle bundle = getIntent().getExtras();
String empStr = bundle.getString("EMP");
            Gson gson = new Gson();
            Type type = new TypeToken<Employee>() {
            }.getType();
            Employee selectedEmp = gson.fromJson(empStr, type);
5
répondu DroidNinja 2017-06-23 12:06:01

cette question est également abordée dans une autre question sur le débordement des cheminées. S'il vous plaît jeter un oeil à une solution à passer des données par l'intention en utilisant Serialisable . Le point principal est d'utiliser Bundle objet qui stocke les données nécessaires à l'intérieur de Intent .

 Bundle bundle = new Bundle();

 bundle.putSerializable(key1, value1);
 bundle.putSerializable(key2, value2);
 bundle.putSerializable(key3, value3);

 intent.putExtras(bundle);

pour extraire les valeurs:

 Bundle bundle = new Bundle();

 for (String key : bundle.keySet()) {
 value = bundle.getSerializable(key));
 }

avantage de Serializable est sa simplicité. Cependant, vous devez envisagez d'utiliser la méthode Parcelable si vous avez besoin de nombreuses données à transférer, parce que Parcelable est spécifiquement conçu pour Android et il est plus efficace que Serializable . Vous pouvez créer Parcelable classe en utilisant:

  1. un outil en ligne - parcelabler
  2. un plugin pour Android Studio - générateur de code mobile Android
5
répondu Sa Qada 2017-10-16 12:19:43

Oui, utiliser un objet statique est de loin la façon la plus facile de le faire avec des objets personnalisés non-sérialisables.

3
répondu alistair 2011-05-13 21:49:45

les objets D'Activité Android peuvent être détruits et reconstitués. Donc, vous aurez besoin d'utiliser une autre approche pour regarder eux - ou tout objet qu'ils créent !!! - jusqu'. C'est-à-dire que vous pourriez passer pour une référence de classe statique, mais alors le handle d'objet (Java appelle ces "références", comme le fait SmallTalk; mais ce ne sont pas des références au sens de C ou assembly) sera peut-être invalide plus tard parce qu'une" fonctionnalité " D'OE Android est toute activité peut être annihilée et reconstituée tard.

la question originale demandé" Comment passer objet d'une activité à une autre dans Android " et personne n'a répondu que. Bien sûr, vous pouvez sérialiser (sérialisable, séparable, vers/depuis JSON) et passer une copie des données de l'objet et un nouvel objet ayant les mêmes données pourrait être créé; mais il n'aura pas les mêmes références/poignées. Aussi, beaucoup d'autres ont mentionné que vous pouvez stocker la référence dans un magasin statique. Et ça va marcher à moins que Android décide d'ondestroyer votre Activité.

donc, pour vraiment résoudre la question originale, vous auriez besoin d'une recherche statique plus chaque objet mettra à jour sa référence quand/si elle est recréée. Par exemple: chaque activité Android se reliserait si son onCreate est appelé. Vous pouvez également voir comment certaines personnes utilisent la liste des tâches pour rechercher une activité par son nom. (système est en train de détruire temporairement cette instance de l'activité pour économiser de l'espace..getRunningTasks, la liste des tâches est effectivement une liste spécialisée des l'exemple d'objet le plus récent de chaque activité).

pour référence:

arrêté: "L'activité est complètement masqué par une autre activité (l'activité est maintenant dans le "fond"). Une activité arrêtée est également toujours en vie (l'objet D'activité est conservé en mémoire , il conserve toutes les informations sur l'état et les membres, mais n'est pas attaché au gestionnaire de fenêtres). Cependant, il n'est plus visible pour l'utilisateur et il peuvent être tués par le système lorsque la mémoire est nécessaire ailleurs."

onDestroy "le système est temporairement détruire cette instance de l'activité pour économiser de l'espace."

ainsi, le Bus de messages est une solution réalisable. Il fondamentalement des "plates". Plutôt que d'essayer d'avoir des références à des objets, alors vous réorganisez votre design pour utiliser le MessagePassing au lieu du SequentialCode. Exponentiellement plus difficile à déboguer; mais il vous permet de ne tenez pas compte de ce genre de compréhension de L'environnement opérationnel. En effet, chaque accès de méthode objet est inversé de sorte que l'appelant affiche un Message et l'objet lui-même définit un gestionnaire pour ce message. Beaucoup plus de code, mais peut le rendre robuste avec les restrictions OE Android.

si tout ce que vous voulez est L'activité supérieure (chose typique dans les applications Android en raison du "contexte" étant nécessaire partout), alors vous pouvez juste avoir chaque activité se répertorie comme "haut" dans l'espace statique mondial chaque fois que son onResume est appelé. Alors votre AlertDialog ou n'importe quoi qui a besoin d'un contexte peut simplement l'attraper de là. Aussi, c'est un peu malchanceux d'utiliser un global mais peut simplifier passer un contexte de haut en bas partout et, pour sûr, quand vous utilisez un MessageBus alors il est global de toute façon.

3
répondu TimJowers2 2014-09-08 15:26:02
  1. je sais que la statique est mauvaise, mais il semble que nous sommes forcés de l'utiliser ici. Le problème avec parceables / seriazables est que les deux activités ont des instances dupliquées du même objet = perte de mémoire et CPU.

    public class IntentMailBox {
        static Queue<Object> content = new LinkedList<Object>();
    }
    

activité appelant

IntentMailBox.content.add(level);
Intent intent = new Intent(LevelsActivity.this, LevelActivity.class);
startActivity(intent);

activité appelée (notez que onCreate () et onResume () peut être appelé plusieurs fois lorsque le système détruit et recrée des activités)

if (IntentMailBox.content.size()>0)
    level = (Level) IntentMailBox.content.poll();
else
    // Here you reload what you have saved in onPause()
  1. une Autre façon est de déclarer un champ statique de la classe que vous souhaitez passer dans la classe. Il servira uniquement à cette fin. N'oubliez pas qu'il peut être nul dans onCreate, parce que votre paquet app a été déchargé de la mémoire par le système et rechargé plus tard.

  2. en gardant à l'esprit que vous avez encore besoin de gérer le cycle de vie de l'activité, vous pouvez vouloir écrire toutes les données directement aux préférences partagées, douloureux avec des structures de données complexes comme il est.

2
répondu Anton Duzenko 2015-11-22 13:45:20

ci-dessus réponses presque toutes correctes, mais pour ceux qui ne sous-estime pas et ces réponses Android a powerfull classe intention avec l'aide de celle-ci, vous partagez des données entre non seulement l'activité, mais d'autres composants D'Android (Récepteur de diffusion, servises pour le contenu de fournir que nous utilisons ContetnResolver classe aucune intention). Dans votre activité vous construisez intention

Intent intent = new Intent(context,SomeActivity.class);
intent.putExtra("key",value);
startActivity(intent);

dans votre activité de recul vous avez

public class SomeActivity extends AppCompactActivity {

    public void onCreate(...){
    ...
          SomeObject someObject = getIntent().getExtras().getParceable("key");
    }

}

You doivent mettre en œuvre L'interface Parceable ou sérialisable sur votre objet afin de partager entre les activités. Il est difficile de mettre en œuvre Parcealbe plutôt que Serialisable interface sur l'objet c'est pourquoi android a plugin spécialement pour cela.Téléchargez-le et utilisez-le

1
répondu Sardor Islomov 2017-03-14 16:42:07

je me suis toujours demandé pourquoi cela ne peut pas être aussi simple que d'appeler une méthode de l'autre activité. J'ai récemment écrit une bibliothèque utilitaire qui le rend presque aussi simple que cela. Vous pouvez le consulter ici ( https://github.com/noxiouswinter/gnlib_android/wiki/gnlauncher ).

GNLauncher rend l'envoi d'objets/données à une activité à partir d'une autre activité etc aussi facile que l'appel d'une fonction dans l'activité avec le données requises comme paramètres. Il introduit la sécurité de type et supprime tous les hastles de devoir serialize, attachant à l'intention en utilisant des clés de chaîne et de défaire la même à l'autre extrémité.

Utilisation

définissez une interface avec les méthodes que vous souhaitez utiliser pour lancer l'activité.

public interface IPayload {
    public void sayHello(String name, int age);
}

implémenter l'interface ci-dessus sur l'activité à lancer. Prévenez également GNLauncher lorsque l'activité est prête.

public class Activity_1 extends Activity implements IPayload {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        //Notify GNLauncher when the Activity is ready. 
        GNLauncher.get().ping(this);
    }

    @Override
    public void sayHello(String name, int age) {
        Log.d("gnlib_test", "Hello " + name + "! \nYour age is: " + age);
    }
}

Dans l'autre Activité, obtenir un proxy à l'Activité ci-dessus et appeler n'importe quelle méthode avec les paramètres souhaités.

public class Activity_2 extends Activity {
    public void onClick(View v) {
        ((IPayload)GNLauncher.get().getProxy(this, IPayload.class, Activity_1.class)).sayHello(name, age);
    }
}

La première activité sera lancée et la méthode appelée avec les paramètres requis.

prérequis

consultez https://github.com/noxiouswinter/gnlib_android/wiki#prerequisites pour plus d'informations sur la façon d'ajouter les dépendances.

0
répondu jinais 2015-01-07 18:36:33

passer l'objet d'une activité à une autre.

(1) activité de la source

Intent ii = new Intent(examreport_select.this,
                    BarChartActivity.class);

            ii.putExtra("IntentExamResultDetail",
                    (Serializable) your List<ArraList<String>> object here);
            startActivity(ii);

(2) destination acitivité

List<ArrayList<String>> aa = (List<ArrayList<String>>) getIntent()
            .getSerializableExtra("IntentExamResultDetail");
0
répondu Jayesh Kalkani 2015-07-13 05:48:30

j'ai utilisé pour mettre objet avec Pacelable ou Serialisable à transférer, mais chaque fois que j'ajoute d'autres variables à Objet(model), je dois tout enregistrer. C'est tellement nconvenient.

il est très facile de transférer un objet entre des activités ou des fragments.

Android DataCache

0
répondu kimkevin 2015-10-04 11:44:57

nous pouvons passer l'objet d'une activité à une autre:

SupplierDetails poSuppliersDetails = new SupplierDetails();

à l'Intérieur poSuppliersDetails nous avons des valeurs. Maintenant, j'envoie cet objet à l'activité cible:

Intent iPODetails = new Intent(ActivityOne.this, ActivityTwo.class);
iPODetails.putExtra("poSuppliersDetails", poSuppliersDetails);

Comment obtenir ce ACtivityTwo:

private SupplierDetails supplierDetails;
    supplierDetails =(SupplierDetails) getIntent().getSerializableExtra("poSuppliersDetails");
0
répondu Peter Mortensen 2015-11-22 15:04:36

passer D'une activité à une autre:

startActivity(new Intent(getBaseContext(),GetActivity.class).putExtra("passingkey","passingvalue"));

Obtenir les valeurs:

String myvalue= getIntent().getExtras("passingkey");
0
répondu Bhuvaneshwaran Vellingiri 2017-05-29 14:24:52

Bonjour à tous, je vois beaucoup de bonnes options, mais je me demandais pourquoi la Liaison n'a pas été utilisé?

passer une référence à un objet me semble juste plus efficace que de sérialiser et de desteriliser des objets, mais je n'ai pas fait de plongée profonde pour voir si c'est ce qui se passe dans les coulisses.

créer un classeur est assez simple...

public class MyBinder extends Binder {

    private Object myObject;

    public MyBinder(Object object) {
        myObject = object;
    }

    public Object getObject() {
        return myObject;
    }

}

et la création du parcelable pour l'utiliser n'est pas mauvais de l'éther.

public class MyParcelable implements Parcelable {

    private Object myObject;

    public MyParcelable() {
    }

    public MyParcelable(Parcel parcel) {
        myObject = ((MyBinder)parcel.readStrongBinder()).getObject();
    }

    public void setObject(Object object) {
        myObject = object;
    }

    public Object getObject() {
        return myObject;
    }

    public void writeToParcel(Parcel parcel, int flags) {
        parcel.writeStrongBinder(new MyBinder(myObject));
    }

    public int describeContents() {
        return myObject == null ? 0 : 1;
    }

    public static final Parcelable.Creator<MyParcelable> CREATOR = new Parcelable.Creator<MyParcelable>() {

        public MyParcelable createFromParcel(Parcel parcel) {
            return new MyParcelable(parcel);
        }

        public MyParcelable[] newArray(int length) {
            return new MyParcelable[length];
        }

    };
}

Cette logique est vraiment cool, parce que vous êtes réellement en passant une référence d'activité.

je conseillerais de vérifier pour nulls et si l'instanceof Binder est mon relieur!

et de mettre en œuvre ce que vous venez...

Envoyer

Object myObject = "some object";
MyParcelable myParcelable = new MyParcelable();
myParcelable.setObject(myObject);

intent.putExtra("MyParcelable", myParcelable);

récupérer

myParcelable = (MyParcelable) getIntent().getExtras().getParcelable("MyParcelable");
myObject = myParcelable.getObject();

Heck quelqu'un pourrait devenir fou et faire de ce crétin un vrai Générique.

-1
répondu SkidRunner 2016-07-13 19:03:21