193 lines
6.5 KiB
Java
193 lines
6.5 KiB
Java
package tc.oc.pgm.core;
|
|
|
|
import java.util.Collections;
|
|
import java.util.HashMap;
|
|
import java.util.Map;
|
|
import java.util.Set;
|
|
import javax.annotation.Nonnull;
|
|
import javax.annotation.Nullable;
|
|
|
|
import com.google.common.collect.ImmutableList;
|
|
import net.md_5.bungee.api.chat.BaseComponent;
|
|
import net.md_5.bungee.api.chat.TranslatableComponent;
|
|
import org.bukkit.Location;
|
|
import org.bukkit.Material;
|
|
import org.bukkit.block.Block;
|
|
import org.bukkit.material.MaterialData;
|
|
import org.bukkit.util.Vector;
|
|
import tc.oc.commons.core.chat.Components;
|
|
import tc.oc.commons.bukkit.chat.NameStyle;
|
|
import tc.oc.pgm.match.Competitor;
|
|
import tc.oc.pgm.match.Match;
|
|
import tc.oc.pgm.match.MatchPlayerState;
|
|
import tc.oc.pgm.match.ParticipantState;
|
|
import tc.oc.pgm.goals.ModeChangeGoal;
|
|
import tc.oc.pgm.goals.TouchableGoal;
|
|
import tc.oc.pgm.regions.CuboidRegion;
|
|
import tc.oc.pgm.regions.FiniteBlockRegion;
|
|
import tc.oc.pgm.regions.Region;
|
|
import tc.oc.pgm.teams.Team;
|
|
import tc.oc.pgm.utils.MaterialPattern;
|
|
|
|
public class Core extends TouchableGoal<CoreFactory> implements ModeChangeGoal<CoreFactory> {
|
|
|
|
protected final FiniteBlockRegion casingRegion;
|
|
protected final FiniteBlockRegion lavaRegion;
|
|
protected final Region leakRegion;
|
|
|
|
protected MaterialData material;
|
|
protected boolean leaked = false;
|
|
protected Iterable<Location> proximityLocations;
|
|
protected Map<MatchPlayerState, Material> breakers;
|
|
|
|
public Core(CoreFactory definition, Match match) {
|
|
super(definition, match);
|
|
|
|
this.material = definition.getMaterial();
|
|
|
|
Region region = definition.getRegion();
|
|
|
|
final FiniteBlockRegion.Factory regionFactory = new FiniteBlockRegion.Factory(match.getMapInfo().proto);
|
|
|
|
this.casingRegion = regionFactory.fromWorld(region, match.getWorld(), new MaterialPattern(this.material));
|
|
if(this.casingRegion.blockVolume() == 0) {
|
|
match.getServer().getLogger().warning("No casing material (" + this.material + ") found in core " + this.getName());
|
|
}
|
|
|
|
this.lavaRegion = regionFactory.fromWorld(region,
|
|
match.getWorld(),
|
|
new MaterialPattern(Material.LAVA, (byte) 0),
|
|
new MaterialPattern(Material.STATIONARY_LAVA, (byte) 0));
|
|
if(this.lavaRegion.blockVolume() == 0) {
|
|
match.getServer().getLogger().warning("No lava found in core " + this.getName());
|
|
}
|
|
|
|
Vector min = new Vector(region.getBounds().minimum()).subtract(new Vector(15, 0, 15));
|
|
min.setY(0);
|
|
Vector max = new Vector(region.getBounds().maximum()).add(new Vector(15, 0, 15));
|
|
max.setY(region.getBounds().minimum().getY() - definition.getLeakLevel());
|
|
this.leakRegion = new CuboidRegion(min, max);
|
|
this.breakers = new HashMap<>();
|
|
}
|
|
|
|
// Remove @Nullable
|
|
@Override
|
|
public @Nonnull Team getOwner() {
|
|
return super.getOwner();
|
|
}
|
|
|
|
@Override
|
|
public boolean getDeferTouches() {
|
|
return true;
|
|
}
|
|
|
|
@Override
|
|
public BaseComponent getTouchMessage(@Nullable ParticipantState toucher, boolean self) {
|
|
if(toucher == null) {
|
|
return new TranslatableComponent("match.touch.core.owner",
|
|
Components.blank(),
|
|
getComponentName(),
|
|
getOwner().getComponentName());
|
|
} else if(self) {
|
|
return new TranslatableComponent("match.touch.core.owner.you",
|
|
Components.blank(),
|
|
getComponentName(),
|
|
getOwner().getComponentName());
|
|
} else {
|
|
return new TranslatableComponent("match.touch.core.owner.toucher",
|
|
toucher.getStyledName(NameStyle.COLOR),
|
|
getComponentName(),
|
|
getOwner().getComponentName());
|
|
}
|
|
}
|
|
|
|
@Override
|
|
public Iterable<Location> getProximityLocations(ParticipantState player) {
|
|
if(proximityLocations == null) {
|
|
proximityLocations = Collections.singleton(casingRegion.getBounds().center().toLocation(this.getMatch().getWorld()));
|
|
}
|
|
return proximityLocations;
|
|
}
|
|
|
|
public MaterialData getMaterial() {
|
|
return this.material;
|
|
}
|
|
|
|
public FiniteBlockRegion getCasingRegion() {
|
|
return this.casingRegion;
|
|
}
|
|
|
|
public FiniteBlockRegion getLavaRegion() {
|
|
return this.lavaRegion;
|
|
}
|
|
|
|
public Region getLeakRegion() {
|
|
return this.leakRegion;
|
|
}
|
|
|
|
public void markLeaked() {
|
|
this.leaked = true;
|
|
}
|
|
|
|
public boolean hasLeaked() {
|
|
return this.leaked;
|
|
}
|
|
|
|
@Override
|
|
public boolean canComplete(Competitor team) {
|
|
return team != this.getOwner();
|
|
}
|
|
|
|
@Override
|
|
public boolean isCompleted() {
|
|
return this.leaked;
|
|
}
|
|
|
|
@Override
|
|
public boolean isCompleted(Competitor team) {
|
|
return this.leaked && this.canComplete(team);
|
|
}
|
|
|
|
@Override
|
|
public boolean isAffectedByModeChanges() {
|
|
return this.definition.hasModeChanges();
|
|
}
|
|
|
|
@Override
|
|
@SuppressWarnings("deprecation")
|
|
public void replaceBlocks(MaterialData newMaterial) {
|
|
for(Block block : this.getCasingRegion().getBlocks(match.getWorld())) {
|
|
if(this.isObjectiveMaterial(block)) {
|
|
block.setTypeIdAndData(newMaterial.getItemTypeId(), newMaterial.getData(), true);
|
|
}
|
|
}
|
|
this.material = newMaterial;
|
|
}
|
|
|
|
@Override
|
|
@SuppressWarnings("deprecation")
|
|
public boolean isObjectiveMaterial(Block block) {
|
|
return block.getType() == this.material.getItemType() && block.getData() == this.material.getData();
|
|
}
|
|
|
|
@Override
|
|
public String getModeChangeMessage() {
|
|
return "match.objectiveMode.name.core";
|
|
}
|
|
|
|
@Override
|
|
public void touch(@Nullable ParticipantState toucher) {
|
|
super.touch(toucher);
|
|
breakers.putIfAbsent(toucher, material.getItemType());
|
|
}
|
|
|
|
public ImmutableList<CoreContribution> getContributions() {
|
|
Set<ParticipantState> touchers = getTouchingPlayers();
|
|
ImmutableList.Builder<CoreContribution> builder = ImmutableList.builder();
|
|
for(MatchPlayerState player : touchers) {
|
|
builder.add(new CoreContribution(player, 1d / touchers.size(), breakers.get(player)));
|
|
}
|
|
return builder.build();
|
|
}
|
|
}
|