首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Libgdx自定义Array<Vector2>序列化

Libgdx自定义Array<Vector2>序列化
EN

Stack Overflow用户
提问于 2014-11-07 09:05:28
回答 3查看 1.4K关注 0票数 2

我正在尝试编写一个自定义JSON序列化程序,它可以作为Vector2对象的坐标在浮动数组中读取。假设我的类中有一个数组名为:

代码语言:javascript
复制
Array<Vector2> splinePoints;

我希望能够读写JSON文件,格式如下:

代码语言:javascript
复制
splinePoints: [0,0, 1,1, 2,2]

每对浮点数被读取为Vector2对象的x和y坐标。这种格式允许我复制和粘贴由Inkscape生成的样条点,只需进行最少的编辑。此外,这比使用默认序列化程序的表单更紧凑:

代码语言:javascript
复制
splinePoints: [{x: 0, y: 0}, {x: 1, y: 1}, {x: 2, y: 2}]

到目前为止,我已经尝试过以下代码(这可能是非常错误的):

代码语言:javascript
复制
public class PointsHolder {
    public Array<Vector2> splinePoints = new Array<Vector2>();
}

Json json = new Json();
json.setSerializer(PointsHolder.class, new Json.Serializer<PointsHolder>() {
    public void write(Json json, PointsHolder pointsHolder, Class knownType) {
        json.writeArrayStart();
        for(Vector2 vector2: pointsHolder.splinePoints) {
            json.writeValue(vector2.x);
            json.writeValue(vector2.y);
        }
        json.writeArrayEnd();
    }

    public PointsHolder read(Json json, JsonValue jsonData, Class type) {
        PointsHolder pointsHolder = new PointsHolder();
        for (JsonValue child = jsonData.child; child != null; child = child.next) {
            Vector2 vector2 = new Vector2();
            vector2.x = jsonData.child.asFloat();
            vector2.y = jsonData.child.next.asFloat();
            pointsHolder.splinePoints.add(vector2);
        }

        return pointsHolder;
    }
});

当运行时,我得到一个异常,它无法将值转换为所需的类型。即使在阅读了教程并阅读了源代码之后,我仍然很难理解JSON序列化程序是如何工作的。当读取数组时,JsonValue jsonData指的是什么?第三个参数“类”在读和写方法中是用来做什么的?我是否需要为Array.class而不是Vector2.class编写序列化程序,尽管我仍然希望对不属于Vector2类型的数组使用默认的序列化程序?

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2014-11-08 07:36:52

问题在于您的read()方法。您在循环中使用jsonData.child,它始终是第一个元素。试一试:

代码语言:javascript
复制
public PointsHolder read(Json json, JsonValue jsonData, Class type) {
    PointsHolder pointsHolder = new PointsHolder();
    for (JsonValue child = jsonData.child; child != null; child = child.next.next) {
        Vector2 vector2 = new Vector2();
        vector2.x = child.asFloat();
        vector2.y = child.next.asFloat();
        pointsHolder.splinePoints.add(vector2);
    }

    return pointsHolder;
}

我用最新的版本测试了这段代码,它可以工作。

更新:我已经用字符串[0,0, 1,1, 2,2]测试了代码。如果您想反序列化类似的

代码语言:javascript
复制
{
  splinePoints: [0,0, 1,1, 2,2]
}

您必须用新类包装您的PointsHolder。类似于:

代码语言:javascript
复制
public class PointsHolderWrapper
{
    public PointsHolder splinePoints;
}
票数 3
EN

Stack Overflow用户

发布于 2014-11-07 12:04:49

我认为你在这里的问题是你在错误的水平上这样做。

要执行您想做的事情,您的序列化代码应该放在包含splinePoints数组的类中。

当你拥有它的时候,你的作者就会产生

代码语言:javascript
复制
splinePoints: [[0,0],[1,1],[2,2]]

在这里看看我们的开源libGdx游戏

特别是在执行完全序列化的Profile类以及从手工创建的文件中读取的AchievementManager和LeaderboardManager类中。

你可能想做些类似的事情

代码语言:javascript
复制
json.writeArrayStart();
for(Vector2 v : splinePoints) {
    json.writeValue(v.x);
    json.writeValue(v.y);
}
json.writeArrayEnd();
票数 0
EN

Stack Overflow用户

发布于 2014-11-07 18:20:37

这是对json数组的序列化:

代码语言:javascript
复制
class PointsHolder {
Array<Vector2> splinePoints;

// some setters/getters
}

// in your code instead of field/variable:
Array<Vector2> splinePoints;

// use:
PointsHolder splinePointsHolder;

然后向splinePointsHolder添加一些项并将其序列化。序列化器应该创建json数组,并在其中添加splinePoints列表中的所有项(如果序列化是为Vector2定义的)。此外,您可能需要使用受支持的列表/数组(如果json序列化程序不支持Array )。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/26797620

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档