crwdns126031:0crwdne126031:0

crwdns126033:0crwdne126033:0

crwdns126035:0:javadoc:crwdne126035:0

  1. crwdns126037:0crwdne126037:0

  2. crwdns126039:0:javadoc:crwdne126039:0

crwdns126041:0crwdne126041:0

  1. crwdns126043:0:javadoc:crwdne126043:0

  2. crwdns126045:0crwdne126045:0

  3. crwdns126047:0:javadoc:crwdne126047:0

crwdns126049:0crwdne126049:0

Note

crwdns126051:0:doc:crwdne126051:0

crwdns126053:0crwdne126053:0

import org.spongepowered.common.data.DataProcessor;
import org.spongepowered.common.data.ValueProcessor;
import org.spongepowered.common.data.manipulator.immutable.entity.ImmutableSpongeHealthData;
import org.spongepowered.common.data.manipulator.mutable.common.AbstractData;
import org.spongepowered.common.data.manipulator.mutable.entity.SpongeHealthData;
import org.spongepowered.common.data.processor.common.AbstractEntityDataProcessor;
import org.spongepowered.common.util.Constants;
import org.spongepowered.common.data.util.NbtDataUtil;
import org.spongepowered.common.registry.type.data.KeyRegistryModule;

crwdns126055:0crwdne126055:0

crwdns126057:0:javadoc:crwdne126057:0

public class SpongeHealthData extends AbstractData<HealthData, ImmutableHealthData> implements HealthData {
    [...]
}

crwdns126059:0crwdne126059:0

crwdns126061:0crwdne126061:0

crwdns126063:0crwdne126063:0

  • crwdns126065:0crwdne126065:0

  • crwdns126067:0crwdne126067:0

crwdns126069:0crwdne126069:0

  • crwdns126071:0crwdne126071:0

  • crwdns126073:0crwdne126073:0

  • crwdns126075:0crwdne126075:0

import static com.google.common.base.Preconditions.checkArgument;

public class SpongeHealthData extends AbstractData<HealthData, ImmutableHealthData> implements HealthData {

    private double health;
    private double maxHealth;

    public SpongeHealthData() {
        this(20D, 20D);
    }

    public SpongeHealthData(double health, double maxHealth) {
        super(HealthData.class);
        checkArgument(maxHealth > 0);
        this.health = health;
        this.maxHealth = maxHealth;
        registerGettersAndSetters();
    }

    [...]

}

crwdns126077:0crwdne126077:0

Note

crwdns126079:0crwdne126079:0

crwdns126081:0crwdne126081:0

crwdns126083:0:javadoc:crwdnd126083:0:javadoc:crwdnd126083:0:javadoc:crwdne126083:0

public MutableBoundedValue<Double> health() {
    return SpongeValueFactory.boundedBuilder(Keys.HEALTH)
        .minimum(0)
        .maximum(this.maxHealth)
        .defaultValue(this.maxHealth)
        .actualValue(this.health)
        .build();
}

Tip

crwdns126085:0crwdne126085:0

crwdns126087:0:javadoc:crwdne126087:0

crwdns126089:0crwdne126089:0

crwdns126091:0:javadoc:crwdnd126091:0:javadoc:crwdne126091:0

crwdns126093:0:javadoc:crwdnd126093:0:javadoc:crwdnd126093:0:javadoc:crwdnd126093:0:javadoc:crwdnd126093:0:javadoc:crwdne126093:0

public DataContainer toContainer() {
    return super.toContainer()
        .set(Keys.HEALTH, this.health)
        .set(Keys.MAX_HEALTH, this.maxHealth);
}

crwdns126095:0crwdne126095:0

crwdns126097:0crwdne126097:0

  • crwdns126099:0:javadoc:crwdne126099:0

  • crwdns126101:0:javadoc:crwdne126101:0

  • crwdns126103:0crwdne126103:0

crwdns126105:0crwdne126105:0

private SpongeHealthData setCurrentHealthIfValid(double value) {
    if (value >= 0 && value <= (double) Float.MAX_VALUE) {
        this.health = value;
    } else {
        throw new IllegalArgumentException("Invalid value for current health");
    }
    return this;
}

private SpongeHealthData setMaximumHealthIfValid(double value) {
    if (value >= 0 && value <= (double) Float.MAX_VALUE) {
        this.maxHealth = value;
    } else {
        throw new IllegalArgumentException("Invalid value for maximum health");
    }
    return this;
}

private void registerGettersAndSetters() {
    registerFieldGetter(Keys.HEALTH, () -> this.health);
    registerFieldSetter(Keys.HEALTH, this::setCurrentHealthIfValid);
    registerKeyValue(Keys.HEALTH, this::health);

    registerFieldGetter(Keys.MAX_HEALTH, () -> this.maxHealth);
    registerFieldSetter(Keys.MAX_HEALTH, this::setMaximumHealthIfValid);
    registerKeyValue(Keys.MAX_HEALTH, this::maxHealth);
}

crwdns126107:0:javadoc:crwdne126107:0

Tip

crwdns126109:0crwdne126109:0

crwdns126111:0crwdne126111:0

crwdns126113:0crwdne126113:0

crwdns126115:0:javadoc:crwdne126115:0

crwdns126117:0crwdne126117:0

  • crwdns126119:0crwdne126119:0

  • crwdns126121:0crwdne126121:0

  • crwdns126123:0crwdne126123:0

crwdns126125:0crwdne126125:0

Tip

crwdns126127:0crwdne126127:0

crwdns126129:0crwdne126129:0

crwdns126131:0:javadoc:crwdnd126131:0:javadoc:crwdne126131:0

import static org.spongepowered.api.data.DataQuery.of;

this.register("health", Key.builder()
        .type(TypeTokens.BOUNDED_DOUBLE_VALUE_TOKEN)
        .id("health")
        .name("Health")
        .query(of("Health"))
        .build());
this.register("max_health", Key.builder()
        .type(TypeTokens.BOUNDED_DOUBLE_VALUE_TOKEN)
        .id("max_health")
        .name("Max Health")
        .query(of("MaxHealth"))
        .build());

crwdns126133:0:javadoc:crwdnd126133:0:javadoc:crwdne126133:0

crwdns126135:0crwdne126135:0

crwdns126137:0crwdne126137:0

crwdns126139:0crwdne126139:0

crwdns126141:0crwdne126141:0

public class HealthDataProcessor
        extends AbstractEntityDataProcessor<EntityLivingBase, HealthData, ImmutableHealthData> {

    public HealthDataProcessor() {
        super(EntityLivingBase.class);
    }

    [...]

}

crwdns126143:0crwdne126143:0

Tip

crwdns126145:0crwdne126145:0

crwdns126147:0crwdne126147:0

crwdns126149:0crwdne126149:0

crwdns126151:0crwdne126151:0

crwdns126153:0crwdne126153:0

@Override
protected boolean doesDataExist(EntityLivingBase entity) {
    return true;
}

crwdns126155:0crwdne126155:0

crwdns126157:0crwdne126157:0

crwdns126159:0crwdne126159:0

crwdns126161:0crwdne126161:0

@Override
protected boolean set(EntityLivingBase entity, Map<Key<?>, Object> keyValues) {
    entity.getEntityAttribute(SharedMonsterAttributes.MAX_HEALTH)
            .setBaseValue(((Double) keyValues.get(Keys.MAX_HEALTH)).floatValue());
    float health = ((Double) keyValues.get(Keys.HEALTH)).floatValue();
    entity.setHealth(health);
    return true;
}

Tip

crwdns126163:0:javadoc:crwdnd126163:0:doc:crwdnd126163:0:javadoc:crwdne126163:0

Warning

crwdns126165:0:javadoc:crwdne126165:0

crwdns126167:0crwdne126167:0

crwdns126169:0crwdne126169:0

crwdns126171:0crwdne126171:0

crwdns126173:0:javadoc:crwdne126173:0

@Override
public DataTransactionResult remove(DataHolder dataHolder) {
    return DataTransactionResult.failNoData();
}

crwdns126175:0crwdne126175:0

crwdns126177:0crwdne126177:0

crwdns126179:0crwdne126179:0

Warning

crwdns126181:0crwdne126181:0

@Override
protected Map<Key<?>, ?> getValues(EntityLivingBase entity) {
    final double health = entity.getHealth();
    final double maxHealth = entity.getMaxHealth();
    return ImmutableMap.of(Keys.HEALTH, health, Keys.MAX_HEALTH, maxHealth);
}

crwdns126183:0crwdne126183:0

crwdns126185:0crwdne126185:0

crwdns126187:0crwdne126187:0

@Override
public Optional<HealthData> fill(DataContainer container, HealthData healthData) {
    if (!container.contains(Keys.MAX_HEALTH.getQuery()) || !container.contains(Keys.HEALTH.getQuery())) {
        return Optional.empty();
    }
    healthData.set(Keys.MAX_HEALTH, getData(container, Keys.MAX_HEALTH));
    healthData.set(Keys.HEALTH, getData(container, Keys.HEALTH));
    return Optional.of(healthData);
}

crwdns126189:0crwdne126189:0

crwdns126191:0crwdne126191:0

crwdns126193:0crwdne126193:0

crwdns126195:0crwdne126195:0

@Override
protected HealthData createManipulator() {
    return new SpongeHealthData();
}

crwdns126197:0crwdne126197:0

crwdns126199:0crwdne126199:0

crwdns126201:0crwdne126201:0

public class HealthValueProcessor
        extends AbstractSpongeValueProcessor<EntityLivingBase, Double, MutableBoundedValue<Double>> {

    public HealthValueProcessor() {
        super(EntityLivingBase.class, Keys.HEALTH);
    }

    [...]

}

crwdns126203:0crwdne126203:0

Tip

crwdns126205:0crwdne126205:0

crwdns126207:0crwdne126207:0

@Override
protected MutableBoundedValue<Double> constructValue(Double health) {
    return SpongeValueFactory.boundedBuilder(Keys.HEALTH)
        .minimum(0D)
        .maximum(((Float) Float.MAX_VALUE).doubleValue())
        .defaultValue(20D)
        .actualValue(health)
        .build();
}

@Override
protected ImmutableBoundedValue<Double> constructImmutableValue(Double value) {
    return constructValue(value).asImmutable();
}
@Override
protected Optional<Double> getVal(EntityLivingBase container) {
    return Optional.of((double) container.getHealth());
}

crwdns126209:0crwdne126209:0

@Override
protected boolean set(EntityLivingBase container, Double value) {
    if (value >= 0 && value <= (double) Float.MAX_VALUE) {
        container.setHealth(value.floatValue());
        return true;
    }
    return false;
}

crwdns126211:0crwdne126211:0

@Override
public DataTransactionResult removeFrom(ValueContainer<?> container) {
    return DataTransactionResult.failNoData();
}

crwdns126213:0crwdne126213:0

crwdns126215:0crwdne126215:0

crwdns126217:0crwdne126217:0

crwdns126219:0crwdne126219:0

crwdns126221:0crwdne126221:0

DataUtil.registerDataProcessorAndImpl(HealthData.class, SpongeHealthData.class,
        ImmutableHealthData.class, ImmutableSpongeHealthData.class,
        new HealthDataProcessor());

crwdns126223:0crwdne126223:0

crwdns126225:0crwdne126225:0

DataUtil.registerValueProcessor(Keys.HEALTH, new HealthValueProcessor());
DataUtil.registerValueProcessor(Keys.MAX_HEALTH, new MaxHealthValueProcessor());

crwdns126227:0crwdne126227:0

crwdns126229:0crwdne126229:0

@Mixin(BlockHorizontal.class)
public abstract class MixinBlockHorizontal extends MixinBlock {

    [...]

}

crwdns126231:0crwdne126231:0

@Override
public boolean supports(Class<? extends ImmutableDataManipulator<?, ?>> immutable) {
    return super.supports(immutable) || ImmutableDirectionalData.class.isAssignableFrom(immutable);
}

crwdns126233:0crwdne126233:0

@Override
public Optional<BlockState> getStateWithData(IBlockState blockState, ImmutableDataManipulator<?, ?> manipulator) {
    if (manipulator instanceof ImmutableDirectionalData) {
        final Direction direction = ((ImmutableDirectionalData) manipulator).direction().get();
        final EnumFacing facing = DirectionResolver.getFor(direction);
        return Optional.of((BlockState) blockState.withProperty(BlockHorizontal.FACING, facing));
    }
    return super.getStateWithData(blockState, manipulator);
}

crwdns126235:0crwdne126235:0

@Override
public <E> Optional<BlockState> getStateWithValue(IBlockState blockState, Key<? extends BaseValue<E>> key, E value) {
    if (key.equals(Keys.DIRECTION)) {
        final Direction direction = (Direction) value;
        final EnumFacing facing = DirectionResolver.getFor(direction);
        return Optional.of((BlockState) blockState.withProperty(BlockHorizontal.FACING, facing));
    }
    return super.getStateWithValue(blockState, key, value);
}

crwdns126237:0crwdne126237:0

@Override
public List<ImmutableDataManipulator<?, ?>> getManipulators(IBlockState blockState) {
    return ImmutableList.<ImmutableDataManipulator<?, ?>>builder()
            .addAll(super.getManipulators(blockState))
            .add(new ImmutableSpongeDirectionalData(DirectionResolver.getFor(blockState.getValue(BlockHorizontal.FACING))))
            .build();
}

crwdns126239:0crwdne126239:0

crwdns126241:0crwdne126241:0

crwdns126243:0crwdne126243:0