【问题标题】:Pass ArrayList of Parcelable objects throws error传递 Parcelable 对象的 ArrayList 会引发错误
【发布时间】:2016-09-27 13:38:24
【问题描述】:

我有一个带有几个字符串的对象,一个 int 和另一个有 4 个内部对象的对象。他们都实现了 Parcelable。为了生成样板代码,我使用了 Android Studio 的 Parcelable 插件。

尽管所有对象都是可打包的,但我收到以下错误:android.os.BadParcelableException: ClassNotFoundException when unmarshalling: AlbumTrackResponse

POJO 的外观如下:

主要对象:

public class AlbumTrackResponse implements Parcelable {

private String id;
private String albumId;
private String position;
private String title;
private int rate;
private AllServices services;

public AllServices getServices() {
    return services;
}

public void setServices(AllServices services) {
    this.services = services;
}

public String getId() {
    return id;
}

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

public String getAlbumId() {
    return albumId;
}

public void setAlbumId(String albumId) {
    this.albumId = albumId;
}

public String getPosition() {
    return position;
}

public void setPosition(String position) {
    this.position = position;
}

public String getTitle() {
    return title;
}

public void setTitle(String title) {
    this.title = title;
}

public int getRate() {
    return rate;
}

public void setRate(int rate) {
    this.rate = rate;
}


protected AlbumTrackResponse(Parcel in) {
    id = in.readString();
    albumId = in.readString();
    position = in.readString();
    title = in.readString();
    rate = in.readInt();
    services = (AllServices) in.readValue(AllServices.class.getClassLoader());
}

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

@Override
public void writeToParcel(Parcel dest, int flags) {
    dest.writeString(id);
    dest.writeString(albumId);
    dest.writeString(position);
    dest.writeString(title);
    dest.writeInt(rate);
    dest.writeValue(services);
}

@SuppressWarnings("unused")
public static final Parcelable.Creator<AlbumTrackResponse> CREATOR = new Parcelable.Creator<AlbumTrackResponse>() {
    @Override
    public AlbumTrackResponse createFromParcel(Parcel in) {
        return new AlbumTrackResponse(in);
    }

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

}

4 个对象的内部对象

public class AllServices implements Parcelable {

private GigRevService gigrev;
private AppleService apple;
private GoogleService google;
private SpotifyService spotify;

protected AllServices(Parcel in) {
    gigrev = (GigRevService) in.readValue(GigRevService.class.getClassLoader());
    apple = (AppleService) in.readValue(AppleService.class.getClassLoader());
    google = (GoogleService) in.readValue(GoogleService.class.getClassLoader());
    spotify = (SpotifyService) in.readValue(SpotifyService.class.getClassLoader());
}

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

public GigRevService getGigrev() {
    return gigrev;
}

public void setGigrev(GigRevService gigrev) {
    this.gigrev = gigrev;
}

public AppleService getApple() {
    return apple;
}

public void setApple(AppleService apple) {
    this.apple = apple;
}

public GoogleService getGoogle() {
    return google;
}

public void setGoogle(GoogleService google) {
    this.google = google;
}

public SpotifyService getSpotify() {
    return spotify;
}

public void setSpotify(SpotifyService spotify) {
    this.spotify = spotify;
}

@Override
public void writeToParcel(Parcel dest, int flags) {
    dest.writeValue(gigrev);
    dest.writeValue(apple);
    dest.writeValue(google);
    dest.writeValue(spotify);

}

@SuppressWarnings("unused")
public static final Parcelable.Creator<AllServices> CREATOR = new Parcelable.Creator<AllServices>() {
    @Override
    public AllServices createFromParcel(Parcel in) {
        return new AllServices(in);
    }

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

}

这里的内部对象只包含字符串项。

以下是我将 ArrayList 传递给捆绑包的方法:

    bundle.putParcelableArrayList(MediaPlayerService.TRACK_LIST, trackList);

我将项目从活动传递到服务。任何想法为什么我会收到此错误?

编辑:服务类的实现

public class GoogleService implements Parcelable {

private String name;
private String uri;

public String getUri() {
    return uri;
}

public void setUri(String uri) {
    this.uri = uri;
}

public String getName() {
    return name;
}

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

protected GoogleService(Parcel in) {
    name = in.readString();
    uri = in.readString();
}

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

@Override
public void writeToParcel(Parcel dest, int flags) {
    dest.writeString(name);
    dest.writeString(uri);
}

@SuppressWarnings("unused")
public static final Parcelable.Creator<GoogleService> CREATOR = new Parcelable.Creator<GoogleService>() {
    @Override
    public GoogleService createFromParcel(Parcel in) {
        return new GoogleService(in);
    }

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

}

【问题讨论】:

    标签: android parcelable


    【解决方案1】:

    这看起来非常奇怪

    this.services = in.readParcelable(getClass().getClassLoader());

    您指出了错误的类加载器。你必须像这样使用它

    this.services = (AllServices)in.readParcelable(AllServices.class.getClassLoader());

    除此之外,我总是使用这个网站http://www.parcelabler.com/ 来快速生成我的 Parceables。或者你可以这样使用它

    services = (AllServices) in.readValue(AllServices.class.getClassLoader());
    

    【讨论】:

    • 不适用于您给我的线路。或许你可以自己试一试看看。
    • @PopAlex-Cristian 您还必须在每个子类中修复它。除此之外,我还发布了另一种方法。
    • 他必须对他使用的每个类的所有对象成员做同样的事情。
    • 我使用你的网站来创建所有 POJO,我得到了同样的错误。
    【解决方案2】:

    这里:

    protected AllServices(Parcel in) { this.gigrev = in.readParcelable(getClass().getClassLoader()); 
    this.apple = in.readParcelable(getClass().getClassLoader()); 
    this.google = in.readParcelable(getClass().getClassLoader()); 
    this.spotify = in.readParcelable(getClass().getClassLoader()); }
    

    替换为

    protected AllServices(Parcel in) { this.gigrev = in.readParcelable(GigRevService.class.getClassLoader()); 
    this.apple = in.readParcelable(AppleService.class.getClassLoader()); 
    this.google = in.readParcelable(GoogleService.class.getClassLoader()); 
    this.spotify = in.readParcelable(SpotifyService.class.getClassLoader()); }
    

    并替换:

     this.services = in.readParcelable(getClass().getClassLoader());
    

    与:

    this.services = in.readParcelable(AllServices.class.getClassLoader());
    

    您还可以显示 GoogleService 等类吗?每个内部对象的类也必须有一个 Parcelable 创建者并实现 Parcelable 接口。

    【讨论】:

    • 我相应地更改了所有类加载器,我得到了同样的错误。
    • 您是否也在 GoogleService AppleService 等上实现了 Parcelable 接口?
    • 是的,我使用上面的网站重新创建了所有对象上的所有内容
    • 你能展示这些类的 Parcelable 实现吗?我总是手写 Parcelables,不使用任何网站。
    • 我编辑了问题并添加了其中一项服务的示例,其余的看起来都一样。
    猜你喜欢
    • 2011-11-15
    • 1970-01-01
    • 2019-07-30
    • 2014-03-07
    • 2012-10-04
    • 1970-01-01
    • 2019-07-30
    • 2017-08-07
    • 1970-01-01
    相关资源
    最近更新 更多