use of com.elmakers.mine.bukkit.api.block.MaterialBrush in project MagicPlugin by elBukkit.
the class IterateSpell method onCast.
@Override
public SpellResult onCast(ConfigurationSection parameters) {
boolean incrementData = parameters.getBoolean("increment_data", false);
int radius = parameters.getInt("radius", 0);
// radius = (int)(radius * mage.getRadiusMultiplier());
int size = parameters.getInt("size", DEFAULT_SIZE);
boolean reverse = parameters.getBoolean("reverse", false);
boolean requireBlock = parameters.getBoolean("require_block", false);
size = (int) (mage.getConstructionMultiplier() * size);
boolean reverseTargeting = parameters.getBoolean("transparent_reverse", false);
if (reverseTargeting) {
setReverseTargeting(true);
}
Block target = getTargetBlock();
if (target == null) {
return SpellResult.NO_TARGET;
}
if (!hasBuildPermission(target) || !hasBuildPermission(getLocation().getBlock())) {
return SpellResult.INSUFFICIENT_PERMISSION;
}
int iterateBlocks = (int) getLocation().distance(target.getLocation());
if (iterateBlocks <= 0)
return SpellResult.NO_TARGET;
iterateBlocks = Math.min(iterateBlocks, size);
Vector targetLoc = new Vector(target.getX(), target.getY(), target.getZ());
Vector playerLoc = getEyeLocation().toVector();
Vector aim = null;
if (reverse) {
aim = playerLoc;
aim.subtract(targetLoc);
aim.normalize();
} else {
aim = targetLoc;
aim.subtract(playerLoc);
aim.normalize();
targetLoc = playerLoc;
// Move out a bit for safety!
targetLoc.add(aim);
targetLoc.add(aim);
}
MaterialBrush buildWith = getBrush();
buildWith.setTarget(target.getLocation());
buildWith.update(mage, target.getLocation());
for (int dr = 0; dr <= radius; dr++) {
int spokes = 1;
// TODO: Handle radius > 1 algorithmically....
if (dr > 0) {
// 8, 16, 24, 32
spokes = dr * 8;
}
for (int dspoke = 0; dspoke < spokes; dspoke++) {
Vector currentLoc = targetLoc.clone();
if (dr > 0) {
// Arbitrary axis rotation would be better, but... math is hard! :P
// TODO: Arbitrary axis rotation.
double q = dspoke * Math.PI * 2 / spokes;
if (aim.getY() > 0.7) {
Vector axis = new Vector(1, 0, 0);
Vector perp = aim.clone().crossProduct(axis).multiply(dr);
double x = perp.getZ() * Math.sin(q) - perp.getX() * Math.cos(q);
double z = perp.getZ() * Math.cos(q) - perp.getX() * Math.sin(q);
perp.setX(x);
perp.setZ(z);
currentLoc.add(perp);
} else if (aim.getX() > 0.7) {
Vector axis = new Vector(0, 1, 0);
Vector perp = aim.clone().crossProduct(axis).multiply(dr);
double y = perp.getZ() * Math.sin(q) - perp.getY() * Math.cos(q);
double z = perp.getZ() * Math.cos(q) - perp.getY() * Math.sin(q);
perp.setY(y);
perp.setZ(z);
currentLoc.add(perp);
} else {
Vector axis = new Vector(0, 1, 0);
Vector perp = aim.clone().crossProduct(axis).multiply(dr);
double y = perp.getX() * Math.sin(q) - perp.getY() * Math.cos(q);
double x = perp.getX() * Math.cos(q) - perp.getY() * Math.sin(q);
perp.setY(y);
perp.setX(x);
currentLoc.add(perp);
}
}
for (int i = 0; i < iterateBlocks; i++) {
Block currentTarget = target.getWorld().getBlockAt(currentLoc.getBlockX(), currentLoc.getBlockY(), currentLoc.getBlockZ());
if (!isTargetable(currentTarget) && isDestructible(currentTarget) && hasBuildPermission(currentTarget)) {
registerForUndo(currentTarget);
buildWith.update(mage, currentTarget.getLocation());
if (incrementData) {
short data = buildWith.getData();
data = i > 15 ? 15 : (short) i;
buildWith.setData(data);
}
if (requireBlock) {
Block lowerBlock = currentTarget.getRelative(BlockFace.DOWN);
if (lowerBlock.getType() == Material.AIR || lowerBlock.getType() == buildWith.getMaterial()) {
currentLoc.add(aim);
continue;
}
}
buildWith.modify(currentTarget);
controller.updateBlock(currentTarget);
Location effectLocation = currentTarget.getLocation();
effectLocation.add(0.5f, 0.5f, 0.5f);
if (dr == 0) {
Material material = buildWith.getMaterial();
// TODO: Customize with effects system
if (material == Material.AIR) {
effectLocation.getWorld().playEffect(effectLocation, Effect.STEP_SOUND, Material.OBSIDIAN.getId());
} else {
effectLocation.getWorld().playEffect(effectLocation, Effect.STEP_SOUND, material.getId());
}
}
}
currentLoc.add(aim);
}
}
}
registerForUndo();
return SpellResult.CAST;
}
use of com.elmakers.mine.bukkit.api.block.MaterialBrush in project MagicPlugin by elBukkit.
the class TransmuteSpell method onCast.
@Override
public SpellResult onCast(ConfigurationSection parameters) {
BlockList transmuteAction = null;
/*
* Use target if targeting
*/
Block target = getTargetBlock();
if (target != null) {
UndoQueue undoQueue = mage.getUndoQueue();
transmuteAction = undoQueue.getLast(target);
}
if (transmuteAction == null) {
UndoQueue undoQueue = mage.getUndoQueue();
transmuteAction = undoQueue.getLast();
}
if (transmuteAction == null) {
return SpellResult.NO_TARGET;
}
MaterialBrush buildWith = getBrush();
for (BlockData undoBlock : transmuteAction) {
Block block = undoBlock.getBlock();
buildWith.modify(block);
}
return SpellResult.CAST;
}
use of com.elmakers.mine.bukkit.api.block.MaterialBrush in project MagicPlugin by elBukkit.
the class PlaneAction method reset.
@Override
public void reset(CastContext context) {
super.reset(context);
MaterialBrush brush = context.getBrush();
Location targetLocation = context.getTargetLocation();
Location orientLocation = targetLocation.clone();
switch(brushAxis) {
case X:
orientLocation.setY(orientLocation.getY() + 1);
orientLocation.setZ(orientLocation.getZ() + 1);
break;
case Z:
orientLocation.setX(orientLocation.getX() + 1);
orientLocation.setY(orientLocation.getY() + 1);
break;
default:
orientLocation.setX(orientLocation.getX() + 1);
orientLocation.setZ(orientLocation.getZ() + 1);
break;
}
brush.setTarget(orientLocation, targetLocation);
}
use of com.elmakers.mine.bukkit.api.block.MaterialBrush in project MagicPlugin by elBukkit.
the class ModifyBlockAction method perform.
@SuppressWarnings("deprecation")
@Override
public SpellResult perform(CastContext context) {
MaterialBrush brush = context.getBrush();
if (brush == null) {
return SpellResult.FAIL;
}
Block block = context.getTargetBlock();
if (brush.isErase()) {
if (!context.hasBreakPermission(block)) {
return SpellResult.INSUFFICIENT_PERMISSION;
}
} else {
if (!context.hasBuildPermission(block)) {
return SpellResult.INSUFFICIENT_PERMISSION;
}
}
if (commit) {
if (!context.areAnyDestructible(block)) {
return SpellResult.NO_TARGET;
}
} else if (!context.isDestructible(block)) {
return SpellResult.NO_TARGET;
}
Material previousMaterial = block.getType();
byte previousData = block.getData();
Mage mage = context.getMage();
brush.update(mage, context.getTargetSourceLocation());
if (!brush.isDifferent(block)) {
return SpellResult.NO_TARGET;
}
if (!brush.isReady()) {
brush.prepare();
return SpellResult.PENDING;
}
if (!brush.isValid()) {
return SpellResult.FAIL;
}
if (consumeBlocks && !context.isConsumeFree() && !brush.isErase()) {
UndoList undoList = context.getUndoList();
if (undoList != null) {
undoList.setConsumed(true);
}
ItemStack requires = brush.getItemStack(1);
if (!mage.hasItem(requires, consumeVariants)) {
String requiresMessage = context.getMessage("insufficient_resources");
context.sendMessage(requiresMessage.replace("$cost", brush.getName()));
return SpellResult.STOP;
}
mage.removeItem(requires, consumeVariants);
}
if (!commit) {
context.registerForUndo(block);
if (brush.isErase()) {
context.clearAttachables(block);
}
}
UndoList undoList = context.getUndoList();
if (undoList != null) {
undoList.setApplyPhysics(applyPhysics);
}
brush.modify(block, applyPhysics);
boolean spawnFalling = spawnFallingBlocks && previousMaterial != Material.AIR;
if (spawnFalling && fallingProbability < 1) {
spawnFalling = context.getRandom().nextDouble() < fallingProbability;
}
if (spawnFalling) {
Location blockLocation = block.getLocation();
Location blockCenter = new Location(blockLocation.getWorld(), blockLocation.getX() + 0.5, blockLocation.getY() + 0.5, blockLocation.getZ() + 0.5);
Vector fallingBlockVelocity = null;
if (fallingBlockSpeed > 0) {
Location source = context.getTargetCenterLocation();
fallingBlockVelocity = blockCenter.clone().subtract(source).toVector();
fallingBlockVelocity.normalize();
if (fallingBlockDirection != null) {
fallingBlockVelocity.add(fallingBlockDirection).normalize();
}
fallingBlockVelocity.multiply(fallingBlockSpeed);
}
if (fallingBlockVelocity != null && (Double.isNaN(fallingBlockVelocity.getX()) || Double.isNaN(fallingBlockVelocity.getY()) || Double.isNaN(fallingBlockVelocity.getZ()) || Double.isInfinite(fallingBlockVelocity.getX()) || Double.isInfinite(fallingBlockVelocity.getY()) || Double.isInfinite(fallingBlockVelocity.getZ()))) {
fallingBlockVelocity = null;
}
boolean spawned = false;
if (usePhysicsBlocks) {
spawned = context.getController().spawnPhysicsBlock(blockCenter, previousMaterial, previousData, fallingBlockVelocity);
}
if (!spawned) {
FallingBlock falling = block.getWorld().spawnFallingBlock(blockCenter, previousMaterial, previousData);
falling.setDropItem(false);
if (fallingBlockVelocity != null) {
SafetyUtils.setVelocity(falling, fallingBlockVelocity);
}
if (fallingBlockMaxDamage > 0 && fallingBlockFallDamage > 0) {
CompatibilityUtils.setFallingBlockDamage(falling, fallingBlockFallDamage, fallingBlockMaxDamage);
} else {
falling.setHurtEntities(fallingBlocksHurt);
}
context.registerForUndo(falling);
}
}
if (breakable > 0) {
context.registerBreakable(block, breakable);
}
if (backfireChance > 0) {
context.registerReflective(block, backfireChance);
}
if (commit) {
com.elmakers.mine.bukkit.api.block.BlockData blockData = com.elmakers.mine.bukkit.block.UndoList.register(block);
blockData.commit();
}
return SpellResult.CAST;
}
use of com.elmakers.mine.bukkit.api.block.MaterialBrush in project MagicPlugin by elBukkit.
the class CheckBlockAction method isAllowed.
protected boolean isAllowed(CastContext context) {
MaterialBrush brush = context.getBrush();
Block block = context.getTargetBlock();
if (block == null) {
return false;
}
if (allowed != null) {
if (!allowed.testBlock(block))
return false;
} else {
if (brush != null && brush.isErase()) {
if (!context.hasBreakPermission(block)) {
return false;
}
} else {
if (!context.hasBuildPermission(block)) {
return false;
}
}
if (!context.isDestructible(block)) {
return false;
}
}
return true;
}
Aggregations