J'essaie de travailler sur l'envoi d'un objet de ma classe de clients à partir de l'un Activity
et de l'afficher dans un autre Activity
.
Le code de la classe client:
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 de l'un Activity
à l'autre puis afficher les données sur l'autre Activity
.
Comment puis-je y parvenir?
Réponses:
Une option pourrait être de laisser votre classe personnalisée implémenter l'
Serializable
interface, puis vous pouvez passer des instances d'objet dans l'intention supplémentaire en utilisant laputExtra(Serializable..)
variante de laIntent#putExtra()
méthode.Pseudocode :
Remarque: assurez-vous que chaque classe imbriquée de votre classe personnalisée principale a implémenté une interface sérialisable pour éviter toute exception de sérialisation. Par exemple:
la source
Parcelable
EST spécifiquement conçu à cet effet (et beaucoup plus rapidement queSerializable
). Je suis confus.Parcelable
peut être bon pour la vitesse, mais il est compliqué à mettre en œuvre. Et si vous avez 8 objets à passer entre les activités, allez-vous en fabriquer chacunParcelable
? Il serait plus judicieux d'utiliser à laSerializable
place. Lorsque vous implémentez,Parcelable
vous devez ajouter beaucoup de code à la classe et classer les champs de manière très spécifique;Serializable
non. En fin de compte, je pense que cela dépend du nombre d'objets que vous passez et de ce que vous essayez de faire.Serializable
est une interface Java standard. Vous marquez simplement une classe Serializable en implantant l'interface, et Java la sérialisera automatiquement dans certaines situations.Parcelable
est une interface spécifique à Android où vous implémentez vous-même la sérialisation. Il a été créé pour être beaucoup plus efficace que Serializable et pour contourner certains problèmes avec le schéma de sérialisation Java par défautImplémentez votre classe avec Serializable. Supposons que c'est votre classe d'entité:
Nous envoyons l'objet appelé
dene
de l'activité X à l'activité Y. Quelque part dans l'activité X;Dans l'activité Y, nous obtenons l'objet.
C'est ça.
la source
classCastException: java.lang.Long
en le faisant. Pouvez-vous expliquer pourquoi?(Serializable)
l'objet?Vous pouvez générer du code Parcelable pour votre classe en utilisant ce site .
la source
Parcelable
je préfère garder mes classes POJO agnostiques et utiliser AndroidSerializable
.Utilisez gson pour convertir votre objet en JSON et lui transmettre l'intention. Dans la nouvelle activité, convertissez le JSON en objet.
Dans votre
build.gradle
, ajoutez ceci à vos dépendancesDans votre activité, convertissez l'objet en chaîne json:
Dans votre activité de réception, reconvertissez la chaîne json en objet d'origine:
Pour Kotlin c'est la même chose
Transmettez les données
Recevoir les données
la source
En appelant une activité
Dans toClass.java recevoir l'activité par
Veuillez vous assurer que la classe client implémente le colis
la source
D'après mon expérience, il existe trois solutions principales, chacune avec ses inconvénients et ses avantages:
Implémentation de Parcelable
Implémentation de sérialisable
Utilisation d'une bibliothèque de bus d'événements légère (par exemple, EventBus de Greenrobot ou Otto de Square)
Parcelable - rapide et standard Android, mais il a beaucoup de code passe-partout et nécessite des chaînes codées en dur pour référence lors de l'extraction des valeurs (non fortement tapé).
Sérialisable - près de zéro passe-partout, mais c'est l'approche la plus lente et nécessite également des chaînes codées en dur lors de l'extraction des valeurs (non fortement typées).
Bus d'événements - zéro passe-partout, approche la plus rapide et ne nécessite pas de chaînes codées en dur, mais il nécessite une dépendance supplémentaire (bien que généralement léger, ~ 40 Ko)
J'ai publié une comparaison très détaillée autour de ces trois approches, y compris des repères d'efficacité.
la source
J'ai trouvé une méthode simple et élégante:
Méthode 1
Code pour la première activité:
Code pour la deuxième activité:
vous trouverez
objSent
etobjReceived
aurez les mêmeshashCode
, ils sont donc identiques.Mais pourquoi peut-on passer un objet java de cette façon?
En fait, Android Binder créera une référence JNI globale pour l'objet Java et libérera cette référence JNI globale lorsqu'il n'y a pas de référence pour cet objet Java. binder enregistrera cette référence JNI globale dans l'objet Binder.
* ATTENTION: cette méthode fonctionne UNIQUEMENT sauf si les deux activités s'exécutent dans le même processus, sinon lancez ClassCastException à (ObjectWrapperForBinder) getIntent (). GetExtras (). GetBinder ("object_value") *
classe ObjectWrapperForBinder, définition
Méthode 2
Mais la méthode 2 a un petit mais grave problème, 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 un orphelin ou fuite de mémoire, la méthode 1 n'a pas ce problème, car Android Binder gérera 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 utiliserons le fichier aidl
IDataContract.aidl
Code pour la première activité
Code pour la deuxième activité:
changez l'attribut android: process dans AndroidManifest.xml en un nom de processus non vide pour vous assurer que la deuxième activité s'exécute dans un autre processus
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
la méthode 3 ne semble pas assez simple car nous devons implémenter une interface aidl. Si vous voulez simplement faire une tâche simple et que la valeur de retour de la méthode n'est pas nécessaire, nous pouvons utiliser android.os.Messenger
Code de la première activité (expéditeur):
Code de la deuxième activité (récepteur):
Tous les Messenger.send s'exécuteront dans un gestionnaire de manière asynchrone et séquentielle.
En fait, android.os.Messenger est également une interface aidl, si vous avez le code source android, vous pouvez trouver un fichier nommé IMessenger.aidl
la source
Vous pouvez également écrire les données de l'objet dans des chaînes et des entiers temporaires et les transmettre à l'activité. Bien sûr, de cette façon, vous obtenez les données transportées, mais pas l'objet lui-même.
Mais si vous voulez simplement les afficher et ne pas utiliser l'objet dans une autre méthode ou quelque chose comme ça, cela devrait suffire. Je l'ai fait de la même manière pour afficher simplement les données d'un objet dans une autre activité.
Vous pouvez également les passer directement au lieu des ivars temporaires, mais de cette façon, c'est plus clair, à mon avis. En outre, vous pouvez définir les ivars temporaires sur null afin qu'ils soient nettoyés plus tôt par GarbageCollector.
Bonne chance!
Sur une note latérale: remplacez toString () au lieu d'écrire votre propre méthode d'impression.
Comme mentionné dans les commentaires ci-dessous, voici comment récupérer vos données dans une autre activité:
la source
Bundle extras = getIntent().getExtras();
String val = extras.getString("fname");
J'ai créé une classe d'aide singleton qui contient des objets temporaires.
Au lieu de placer vos objets dans Intent, utilisez IntentHelper:
Dans votre nouvelle activité, vous pouvez obtenir l'objet:
Gardez à l'esprit qu'une fois chargé, l'objet est supprimé pour éviter les références inutiles.
la source
BookActivity.getInstance().recommendationResponse
dansRoomsActivity
obj
devientnull
. Pour éviter cela,obj
doit être stocké quelque part pour le récupérer. En effet, la solution Json stocke les données d'objets dans Intent.Il existe deux façons d'accéder aux variables ou aux objets dans d'autres classes ou activités.
A. Base de données
B. Préférences partagées.
C. Sérialisation d'objets.
D. Une classe pouvant contenir des données communes peut être nommée Common Utilities. Cela dépend de toi.
E. Transmission des données via les intentions et l'interface parcelable.
Cela dépend des besoins de votre projet.
A. Base de données
SQLite est une base de données open source intégrée à Android. SQLite prend en charge les fonctionnalités de base de données relationnelles standard telles que la syntaxe SQL, les transactions et les instructions préparées.
Tutoriels
B. Préférences partagées
Supposons que vous souhaitiez stocker le nom d'utilisateur. Il y aura donc maintenant deux choses, un nom d'utilisateur clé , valeur valeur.
Comment conserver
En utilisant putString (), putBoolean (), putInt (), putFloat () et putLong (), vous pouvez enregistrer le dtatype souhaité.
Comment aller chercher
http://developer.android.com/reference/android/content/SharedPreferences.html
C. Sérialisation d'objets
La sérialisation d'objets est utilisée si nous voulons enregistrer un état d'objet pour l'envoyer sur un réseau ou si vous pouvez également l'utiliser pour votre usage.
Utilisez des beans Java et stockez-le comme l'un de ses domaines et utilisez des getters et setter pour cela.
JavaBeans sont des classes Java qui ont des propriétés. Considérez les propriétés comme des variables d'instance privées. Puisqu'ils sont privés, la seule façon d'y accéder depuis l'extérieur de leur classe est par le biais de méthodes dans la classe. Les méthodes qui modifient 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.
Définissez la variable dans votre méthode de messagerie à l'aide de
Utilisez ensuite la sérialisation d'objets pour sérialiser cet objet et dans votre autre classe désérialiser cet objet.
Dans la sérialisation, un objet peut être représenté comme une séquence d'octets qui inclut 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.
Une fois qu'un objet sérialisé a été écrit dans un fichier, il peut être lu à partir du fichier et désérialisé. Autrement dit, les informations de type et les octets qui représentent l'objet et ses données peuvent être utilisés pour recréer l'objet en mémoire.
Si vous voulez un tutoriel pour cela, référez-vous à:
Sérialisation en Java (article de blog)
Obtenir une variable dans d'autres classes (débordement de pile)
D. CommonUtilities
Vous pouvez créer vous-même une classe qui peut contenir des données communes dont vous avez souvent besoin dans votre projet.
Échantillon
E. Transmission de données par des intentions
Veuillez consulter le didacticiel Android - Données de parcelle pour passer d'une activité à l'autre à l'aide de classes de parcelle pour cette option de transmission de données.
la source
Créez votre propre classe
Customer
comme suit:Dans votre
onCreate()
méthodeEn
xyz activity
classe, vous devez utiliser le code suivant:la source
La meilleure façon est d'avoir une classe (appelez-la Control) dans votre application qui contiendra une variable statique de type 'Customer' (dans votre cas). Initialisez la variable dans votre activité A.
Par exemple:
Ensuite, allez à l'activité B et récupérez-la dans la classe Control. N'oubliez pas d'attribuer un null après avoir utilisé la variable, sinon la mémoire sera gaspillée.
la source
Vous voulez maintenant passer l'objet de cette classe dans startActivity. Utilisez simplement ceci:
Cela fonctionne ici car MyClass implémente
Serializable
.la source
Si vous choisissez d'utiliser la façon dont Samuh décrit, n'oubliez pas que seules les valeurs primitives peuvent être envoyées. Autrement dit, des valeurs parcellables. Donc, si votre objet contient des objets complexes, ceux-ci ne suivront pas. Par exemple, des variables comme Bitmap, HashMap etc ... Ce sont difficiles à passer par l'intention.
En général , je vous conseille d'envoyer seulement primitifs comme figurants types de données, comme String, int, booléen , etc. Dans votre cas , il serait:
String fname
,String lname
,int age
etString address
.Mon avis: les objets plus complexes sont mieux partagés en implémentant un ContentProvider , une SDCard , etc. Il est également possible d'utiliser une variable statique , mais cela peut rapidement conduire à un code sujet aux erreurs ...
Mais encore une fois, c'est juste mon opinion subjective.
la source
J'utilise parcelable pour envoyer des données d'une activité à une autre activité. Voici mon code qui fonctionne bien dans mon projet.
En activité, utilisez-le comme ceci:
Dans ActivityB, utilisez-le comme ceci pour obtenir des données:
la source
Vous pouvez essayer d'utiliser cette classe. La limitation est qu'elle ne peut pas être utilisée en dehors d'un processus.
Une activité:
Autre activité:
la source
Démarrez une autre activité à partir de cette activité et passez les paramètres via Bundle Object
Retrouver des données sur une autre activité (YourActivity)
C'est correct pour un type de type de données simple. Mais si vous voulez transmettre des données complexes entre les activités. Vous devez d'abord le sérialiser.
Ici, nous avons le modèle des employés
Vous pouvez utiliser la bibliothèque Gson fournie par Google pour sérialiser les données complexes comme celle-ci
la source
Cette question est également abordée dans une autre question Stack Overflow. Veuillez jeter un œil à une solution pour transmettre des données via l'intention en utilisant Serializable . Le point principal est d'utiliser un
Bundle
objet qui stocke les données nécessaires à l'intérieurIntent
.Pour extraire des valeurs:
L'avantage de
Serializable
sa simplicité. Cependant, vous devriez envisager d'utiliser laParcelable
méthode si vous avez besoin de transférer de nombreuses données, car ilParcelable
est spécialement conçu pour Android et il est plus efficace queSerializable
. Vous pouvez créer uneParcelable
classe en utilisant:la source
Créez une classe comme la classe bean et implémentez l'
Serializable
interface. Ensuite, nous pouvons le passer par laintent
méthode, par exemple:Ensuite, récupérez-le de l'autre activité, par exemple:
la source
Créez deux méthodes dans votre classe personnalisée comme celle-ci
Maintenant, dans votre activité d'expéditeur, faites comme ça
Et dans votre activité de récepteur
la source
Oui, l'utilisation d'un objet statique est de loin la manière la plus simple de le faire avec des objets personnalisés non sérialisables.
la source
static
est la meilleure solution de contournement s'il est tout simplement impossible de continuer à invoquerputExtra()
pour chaque propriété que vous souhaitez transmettre. Par exemple, en ce moment, je veux passer unArrayList
qui contient des objets. Je ferais aussi bien de créer ma liste de tableauxstatic
.Les objets d'activité Android peuvent être détruits et reconstitués. Donc, vous devrez utiliser une autre approche pour les regarder - ou tout objet qu'ils créent !!! - en haut. Autrement dit, vous pouvez passer comme référence de classe statique mais le descripteur 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 d'assemblage) sera peut-être invalide plus tard car une "fonctionnalité" d'Android OE est n'importe quelle activité peut être annihilée et reconstituée plus tard.
La question initiale demandait "Comment passer un objet d'une activité à une autre dans Android" et personne n'a répondu à cela. Bien sûr, vous pouvez sérialiser (Sérialisable, Parcelable, vers / depuis JSON) et transmettre 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. De plus, de nombreux autres ont mentionné que vous pouvez stocker la référence dans un magasin statique. Et cela fonctionnera à moins qu'Android ne décide de détruire votre activité.
Donc, pour vraiment résoudre la question d'origine, vous auriez besoin d'une recherche statique et chaque objet mettra à jour sa référence quand / s'il est recréé. Par exemple, chaque activité Android se réinscrirait si son onCreate était appelé. Vous pouvez également voir comment certaines personnes utilisent la liste des tâches pour rechercher une activité par nom. (le système détruit temporairement cette instance de l'activité pour économiser de l'espace ... getRunningTasks, la liste des tâches est en fait une liste spécialisée de l'instance d'objet la plus récente de chaque activité).
Pour référence:
Ainsi, le Message Bus est une solution viable. Il s'agit essentiellement de "punts". Plutôt que d'essayer d'avoir des références à des objets; puis vous ré-architecturez votre conception pour utiliser MessagePassing au lieu de SequentialCode. Exponentiellement plus difficile à déboguer; mais cela vous permet d'ignorer ce type de compréhension de OperatingEnvironment. En effet, chaque accès à la méthode objet est inversé de sorte que l'appelant publie un message et que l'objet définit lui-même un gestionnaire pour ce message. Beaucoup plus de code mais peut le rendre robuste avec les restrictions Android OE.
Si tout ce que vous voulez, c'est l'activité supérieure (une chose typique dans les applications Android en raison du fait que le "contexte" est nécessaire partout), alors vous pouvez simplement avoir chaque activité elle-même répertoriée comme "top" dans l'espace global statique chaque fois que son onResume est appelé. Ensuite, votre AlertDialog ou tout ce qui a besoin d'un contexte peut simplement le saisir à partir de là. En outre, il est un peu dégoûtant d'utiliser un global mais peut simplifier la transmission d'un contexte de haut en bas partout et, bien sûr, lorsque vous utilisez un MessageBus, alors IL EST global de toute façon.
la source
Je sais que l'électricité statique est mauvaise, mais il semble que nous soyons obligés de l'utiliser ici. Le problème avec les parceables / seriazables est que les deux activités ont des instances en double du même objet = perte de mémoire et de CPU.
Activité d'appel
Activité appelée (notez que onCreate () et onResume () peuvent être appelés plusieurs fois lorsque le système détruit et recrée des activités)
Une autre façon consiste à déclarer un champ statique de la classe que vous souhaitez transmettre dans cette même classe. Il ne servira qu'à cette fin. N'oubliez pas qu'il peut être nul dans onCreate, car votre package d'application a été déchargé de la mémoire par le système et rechargé plus tard.
En gardant à l'esprit que vous devez toujours gérer le cycle de vie de l'activité, vous souhaiterez peut-être écrire toutes les données directement dans les préférences partagées, pénibles avec des structures de données complexes telles quelles.
la source
Les réponses ci-dessus sont presque toutes correctes, mais pour ceux qui ne comprennent pas ces réponses, Android a une classe d' intention puissante à l'aide de celle-ci, vous partagez des données entre non seulement l'activité mais d'autres composants d'Android (récepteur Broadcasr, services pour le contenu à condition d'utiliser la classe ContetnResolver no Intent ). Dans votre activité, vous construisez une intention
Dans votre activité de réception, vous avez
Vous devez implémenter une interface Parceable ou Serializable sur votre objet afin de partager entre les activités. Il est difficile d'implémenter Parcealbe plutôt que l' interface sérialisable sur un objet, c'est pourquoi Android a un plugin spécialement pour cela. Téléchargez-le et utilisez-le
la source
Je m'étais toujours demandé pourquoi cela ne pouvait pas être aussi simple que d'appeler une méthode de l'autre activité. J'ai récemment écrit une bibliothèque d'utilitaires qui la rend presque aussi simple que cela. Vous pouvez le vérifier 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 simple que d'appeler une fonction dans cette activité avec les données requises comme paramètres. Il introduit la sécurité des types et supprime tous les obstacles liés à la sérialisation, à l'attachement à l'intention à l'aide de clés de chaîne et à l'annulation à l'autre extrémité.
Usage
Définissez une interface avec les méthodes que vous souhaitez appeler sur l'activité à lancer.
Implémentez l'interface ci-dessus sur l'activité à lancer. Informez également GNLauncher lorsque l'activité est prête.
Dans l'autre activité, obtenez un proxy pour l'activité ci-dessus et appelez n'importe quelle méthode avec les paramètres souhaités.
La première activité sera lancée et la méthode appelée avec les paramètres requis.
Conditions préalables
Veuillez vous référer à https://github.com/noxiouswinter/gnlib_android/wiki#prerequisites pour plus d'informations sur la façon d'ajouter les dépendances.
la source
Passer l'objet d'une activité à une autre.
(1) activité source
(2) activité de destination
la source
J'avais l'habitude de définir un objet avec Pacelable ou Serializable à transférer, mais chaque fois que j'ajoute d'autres variables à l'objet (modèle), je dois tout enregistrer. C'est tellement gênant.
Il est super facile de transférer un objet entre des activités ou des fragments.
Android DataCache
la source
On peut passer l'objet d'une activité à une autre:
A l'intérieur,
poSuppliersDetails
nous avons quelques valeurs. Maintenant, j'envoie cet objet à l'activité cible:Comment obtenir cela dans ACtivityTwo:
la source
Passer une activité à une autre:
Obtenez des valeurs:
la source
Bonjour à tous, je vois beaucoup de bonnes options, mais je me demandais pourquoi la liaison n'a pas été utilisée?
Créer un classeur est assez simple ...
Et créer la parcellaire pour l'utiliser n'est pas si mauvais que l'éther.
Cette logique est vraiment cool parce que vous passez en fait une référence d'une activité à l'autre.
et pour mettre en œuvre cela, vous venez de ...
Envoyez-le
Récupérer
Heck quelqu'un pourrait devenir fou et faire de ce meunier un vrai générique.
la source