修改實體

確實,生成常規的實體已經很足夠了,不過有沒有更有趣的東西呢?這時候就需要 DataManipulator 大顯身手了。一個 Entity 同時也是一個 DataHolder,也就是說,我們的 Entity 可以儲存資料。關於 DataHolder 的更多資訊可以在 data documentation 找到。

適用於 EntityDataManipulatorFoodDataHealthData 等。適用的 DataManipulator 清單可在 org.spongepowered.api.data.manipulator.mutableorg.spongepowered.api.data.manipulator.mutable.entity 找到。請注意,並非所有 DataManipulator 都適用於所有實體。

實體類型

在我們進一步操作我們的 Entity 之前,我們應該檢查 Entity 是什麼類型,因為我們可能接收到一個不是由我們創造的 Entity,因此不知道其類型。一個簡單的檢查即可完成這一點。以下是一個檢查我們的 Entity 是否為苦力怕的範例:

import org.spongepowered.api.entity.Entity;
import org.spongepowered.api.entity.EntityTypes;

public boolean isCreeper(Entity entity) {
    if (entity.getType().equals(EntityTypes.CREEPER)) {
        return true;
    }
    return false;
}

實體資料操作者(Entity Data Manipulators)

現在我們確定我們的 Entity 是一隻苦力怕了,那我們就可以對其使用針對苦力怕的 DataManipulator。例如 ExplosionRadiusData 是一個苦力怕可以擁有的 DataManipulator,並非所有 Entity 都可以。把一個 Entity 的爆炸範圍改為 50 的範例如下:

import org.spongepowered.api.data.manipulator.mutable.entity.ExplosiveRadiusData;

public void explosionRadius50(Entity creeper) {
    ExplosiveRadiusData radiusData = creeper.get(ExplosiveRadiusData.class).get();
    creeper.offer(radiusData.explosiveRadius().set(50));
}

這將取得我們的 EntityExplosiveRadiusData 來讓我們使用。然後我們使用該資料將苦力怕的爆炸範圍設定為 50,接著我們必須將該資料提供回去給苦力怕,因為我們從我們的 Entity 取得的資料只是一個資料的副本。

也許我們想要給我們的 Entity 一個自定義名稱!這可以透過使用 DisplayNameData 來完成。以下是這個動作的一個範例:

import org.spongepowered.api.data.manipulator.mutable.DisplayNameData;
import org.spongepowered.api.text.Text;
import org.spongepowered.api.text.format.TextColors;

public void setDisplayName(Entity creeper) {
    DisplayNameData displayData = creeper.get(DisplayNameData.class).get();
    creeper.offer(displayData.displayName().set(Text.of(TextColors.DARK_AQUA,
                                                          "Inscrutable")));
}

另外,有更簡短的方式來完成這件事,只要在我們的 Entity 使用 Keys 而非 DataManipulator。就像這樣:

import org.spongepowered.api.data.key.Keys;

public void explosionRadius50(Entity creeper) {
    creeper.offer(Keys.EXPLOSIVE_RADIUS, 50);
    creeper.offer(Keys.DISPLAY_NAME, Text.of(TextColors.DARK_AQUA, "Inscrutable"));
}

這使我們的程式碼更簡潔,也更容易執行。參閱 data documentation 以了解使用 DataManipulatorKeys 的優勢。