mirror of
https://github.com/ClassiCube/MCGalaxy.git
synced 2025-09-24 05:03:34 -04:00
Allow changing animal AI of blocks
This commit is contained in:
parent
a977748936
commit
f2fb839d02
@ -98,14 +98,9 @@ namespace MCGalaxy.Blocks {
|
||||
|
||||
/// <summary> Initalise physics handling behaviour for the core blocks. </summary>
|
||||
internal static void InitCorePhysicsHandlers() {
|
||||
physicsHandlers[Block.birdblack] = BirdPhysics.Do;
|
||||
physicsHandlers[Block.birdwhite] = BirdPhysics.Do;
|
||||
physicsHandlers[Block.birdlava] = BirdPhysics.Do;
|
||||
physicsHandlers[Block.birdwater] = BirdPhysics.Do;
|
||||
physicsHandlers[Block.birdred] = (Level lvl, ref Check C) => HunterPhysics.DoKiller(lvl, ref C, Block.air);
|
||||
physicsHandlers[Block.birdblue] = (Level lvl, ref Check C) => HunterPhysics.DoKiller(lvl, ref C, Block.air);
|
||||
physicsHandlers[Block.birdkill] = (Level lvl, ref Check C) => HunterPhysics.DoKiller(lvl, ref C, Block.air);
|
||||
|
||||
for (int i = 0; i < Block.Count; i++) {
|
||||
physicsHandlers[i] = null;
|
||||
}
|
||||
physicsHandlers[Block.snaketail] = SnakePhysics.DoTail;
|
||||
physicsHandlers[Block.snake] = SnakePhysics.Do;
|
||||
physicsHandlers[Block.rockethead] = RocketPhysics.Do;
|
||||
@ -113,13 +108,6 @@ namespace MCGalaxy.Blocks {
|
||||
physicsHandlers[Block.zombiebody] = ZombiePhysics.Do;
|
||||
physicsHandlers[Block.zombiehead] = ZombiePhysics.DoHead;
|
||||
physicsHandlers[Block.creeper] = ZombiePhysics.Do;
|
||||
|
||||
physicsHandlers[Block.fishbetta] = (Level lvl, ref Check C) => HunterPhysics.DoKiller(lvl, ref C, Block.water);
|
||||
physicsHandlers[Block.fishshark] = (Level lvl, ref Check C) => HunterPhysics.DoKiller(lvl, ref C, Block.water);
|
||||
physicsHandlers[Block.fishlavashark] = (Level lvl, ref Check C) => HunterPhysics.DoKiller(lvl, ref C, Block.lava);
|
||||
physicsHandlers[Block.fishgold] = (Level lvl, ref Check C) => HunterPhysics.DoFlee(lvl, ref C, Block.water);
|
||||
physicsHandlers[Block.fishsalmon] = (Level lvl, ref Check C) => HunterPhysics.DoFlee(lvl, ref C, Block.water);
|
||||
physicsHandlers[Block.fishsponge] = (Level lvl, ref Check C) => HunterPhysics.DoFlee(lvl, ref C, Block.water);
|
||||
|
||||
physicsHandlers[Block.water] = SimpleLiquidPhysics.DoWater;
|
||||
physicsHandlers[Block.activedeathwater] = SimpleLiquidPhysics.DoWater;
|
||||
@ -171,6 +159,9 @@ namespace MCGalaxy.Blocks {
|
||||
physicsHandlers[Block.train] = TrainPhysics.Do;
|
||||
|
||||
for (int i = 0; i < Block.Count; i++) {
|
||||
HandlePhysics animalAI = AnimalAIHandler(Block.Props[i].AnimalAI);
|
||||
if (animalAI != null) { physicsHandlers[i] = animalAI; continue; }
|
||||
|
||||
//Adv physics updating anything placed next to water or lava
|
||||
if ((i >= Block.red && i <= Block.redmushroom) || i == Block.wood ||
|
||||
i == Block.trunk || i == Block.bookcase) {
|
||||
@ -184,5 +175,26 @@ namespace MCGalaxy.Blocks {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static HandlePhysics AnimalAIHandler(AnimalAI ai) {
|
||||
if (ai == AnimalAI.Fly) return BirdPhysics.Do;
|
||||
|
||||
if (ai == AnimalAI.FleeAir) {
|
||||
return (Level lvl, ref Check C) => HunterPhysics.DoFlee(lvl, ref C, Block.air);
|
||||
} else if (ai == AnimalAI.FleeWater) {
|
||||
return (Level lvl, ref Check C) => HunterPhysics.DoFlee(lvl, ref C, Block.water);
|
||||
} else if (ai == AnimalAI.FleeLava) {
|
||||
return (Level lvl, ref Check C) => HunterPhysics.DoFlee(lvl, ref C, Block.lava);
|
||||
}
|
||||
|
||||
if (ai == AnimalAI.KillerAir) {
|
||||
return (Level lvl, ref Check C) => HunterPhysics.DoKiller(lvl, ref C, Block.air);
|
||||
} else if (ai == AnimalAI.KillerWater) {
|
||||
return (Level lvl, ref Check C) => HunterPhysics.DoKiller(lvl, ref C, Block.water);
|
||||
} else if (ai == AnimalAI.KillerLava) {
|
||||
return (Level lvl, ref Check C) => HunterPhysics.DoKiller(lvl, ref C, Block.lava);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -85,7 +85,25 @@ namespace MCGalaxy {
|
||||
Props[wood].LavaKills = true; Props[trunk].LavaKills = true;
|
||||
Props[sponge].LavaKills = true; Props[bookcase].LavaKills = true;
|
||||
Props[leaf].LavaKills = true; Props[crate].LavaKills = true;
|
||||
Props[red].IsRails = true; Props[op_air].IsRails = true;
|
||||
Props[red].IsRails = true; Props[op_air].IsRails = true;
|
||||
|
||||
// Block specific physics properties
|
||||
Props[Block.birdblack].AnimalAI = AnimalAI.Fly;
|
||||
Props[Block.birdwhite].AnimalAI = AnimalAI.Fly;
|
||||
Props[Block.birdlava].AnimalAI = AnimalAI.Fly;
|
||||
Props[Block.birdwater].AnimalAI = AnimalAI.Fly;
|
||||
|
||||
Props[Block.birdred].AnimalAI = AnimalAI.KillerAir;
|
||||
Props[Block.birdblue].AnimalAI = AnimalAI.KillerAir;
|
||||
Props[Block.birdkill].AnimalAI = AnimalAI.KillerAir;
|
||||
|
||||
Props[Block.fishbetta].AnimalAI = AnimalAI.KillerWater;
|
||||
Props[Block.fishshark].AnimalAI = AnimalAI.KillerWater;
|
||||
Props[Block.fishlavashark].AnimalAI = AnimalAI.KillerLava;
|
||||
|
||||
Props[Block.fishgold].AnimalAI = AnimalAI.FleeWater;
|
||||
Props[Block.fishsalmon].AnimalAI = AnimalAI.FleeWater;
|
||||
Props[Block.fishsponge].AnimalAI = AnimalAI.FleeWater;
|
||||
|
||||
SetDefaultNames();
|
||||
SetDefaultDeaths();
|
||||
|
@ -247,11 +247,11 @@ namespace MCGalaxy {
|
||||
|
||||
public static void SetBlocks() {
|
||||
SetCoreProperties();
|
||||
BlockBehaviour.InitCorePhysicsHandlers();
|
||||
BlockProps.Load("core", Block.Props);
|
||||
BlockBehaviour.InitCoreHandlers();
|
||||
|
||||
BlockPerms.Load();
|
||||
|
||||
BlockBehaviour.InitCorePhysicsHandlers();
|
||||
BlockBehaviour.InitCoreHandlers();
|
||||
}
|
||||
|
||||
[Obsolete("Use BlockPerms.CanModify()")]
|
||||
|
@ -21,6 +21,12 @@ using System.IO;
|
||||
|
||||
namespace MCGalaxy.Blocks {
|
||||
|
||||
/// <summary> Type of animal this block behaves as. </summary>
|
||||
public enum AnimalAI : byte {
|
||||
None, Fly, FleeAir, KillerAir, FleeWater, KillerWater, FleeLava, KillerLava,
|
||||
}
|
||||
|
||||
/// <summary> Extended and physics properties of a block. </summary>
|
||||
public struct BlockProps {
|
||||
|
||||
/// <summary> ID of block these properties are associated with. </summary>
|
||||
@ -60,6 +66,9 @@ namespace MCGalaxy.Blocks {
|
||||
/// <summary> Whether this block should allow trains to go over them. </summary>
|
||||
public bool IsRails;
|
||||
|
||||
/// <summary> Animal AI behaviour of this block. </summary>
|
||||
public AnimalAI AnimalAI;
|
||||
|
||||
/// <summary> Whether the properties for this block have been modified and hence require saving. </summary>
|
||||
public bool Changed;
|
||||
|
||||
@ -79,7 +88,7 @@ namespace MCGalaxy.Blocks {
|
||||
using (StreamWriter w = new StreamWriter("blockprops/" + group + ".txt")) {
|
||||
w.WriteLine("# This represents the physics properties for blocks, in the format of:");
|
||||
w.WriteLine("# id : Is rails : Is tdoor : Is door : Is message block : Is portal : " +
|
||||
"Killed by water : Killed by lava : Kills players : death message");
|
||||
"Killed by water : Killed by lava : Kills players : death message : Animal AI type");
|
||||
for (int i = 0; i < scope.Length; i++) {
|
||||
if (!scope[i].Changed) continue;
|
||||
BlockProps props = scope[i];
|
||||
@ -87,7 +96,8 @@ namespace MCGalaxy.Blocks {
|
||||
string deathMsg = props.DeathMessage == null ? "" : props.DeathMessage.Replace(":", "\\;");
|
||||
w.WriteLine(i + ":" + props.IsRails + ":" + props.IsTDoor + ":" + props.IsDoor + ":"
|
||||
+ props.IsMessageBlock + ":" + props.IsPortal + ":" + props.WaterKills + ":"
|
||||
+ props.LavaKills + ":" + props.KillerBlock + ":" + deathMsg);
|
||||
+ props.LavaKills + ":" + props.KillerBlock + ":" + deathMsg + ":"
|
||||
+ (byte)props.AnimalAI);
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -125,6 +135,11 @@ namespace MCGalaxy.Blocks {
|
||||
scope[id].DeathMessage = parts[9].Replace("\\;", ":");
|
||||
if (scope[id].DeathMessage == "")
|
||||
scope[id].DeathMessage = null;
|
||||
|
||||
if (parts.Length > 10) {
|
||||
byte ai; byte.TryParse(parts[10], out ai);
|
||||
scope[id].AnimalAI = (AnimalAI)ai;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -121,7 +121,7 @@ namespace MCGalaxy.Blocks.Physics {
|
||||
CheckAt(lvl, lvl.PosToInt(x, y, (ushort)(z + 1)));
|
||||
CheckAt(lvl, lvl.PosToInt(x, y, (ushort)(z - 1)));
|
||||
CheckAt(lvl, lvl.PosToInt(x, (ushort)(y + 1), z));
|
||||
// ommision of y-1 to match original behaviour
|
||||
// ommission of y-1 to match original behaviour
|
||||
}
|
||||
|
||||
internal static void CheckAt(Level lvl, int index) {
|
||||
|
@ -120,11 +120,15 @@ namespace MCGalaxy.Commands.World {
|
||||
} else if (prop == "deathmsg" || prop == "deathmessage") {
|
||||
string msg = args.Length > 3 ? args[3] : null;
|
||||
SetDeathMessage(p, scope, id, msg);
|
||||
} else if (prop == "animalai" || prop == "animal") {
|
||||
string msg = args.Length > 3 ? args[3] : null;
|
||||
SetEnum(p, scope, id, msg);
|
||||
} else {
|
||||
Help(p);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
delegate void BoolSetter(ref BlockProps props);
|
||||
static void Toggle(Player p, BlockProps[] scope, byte id, string type,
|
||||
BoolSetter setter, Func<BlockProps, bool> getter) {
|
||||
@ -136,7 +140,18 @@ namespace MCGalaxy.Commands.World {
|
||||
Player.Message(p, "Block {0} is {1}: {2}",
|
||||
BlockName(scope, lvl, id),
|
||||
type, getter(props) ? "&aYes" : "&cNo");
|
||||
OnPropsChanged(scope, lvl, id);
|
||||
OnPropsChanged(scope, lvl, id, false);
|
||||
}
|
||||
|
||||
static void SetEnum(Player p, BlockProps[] scope, byte id, string msg) {
|
||||
Level lvl = Player.IsSuper(p) ? null : p.level;
|
||||
AnimalAI ai = AnimalAI.None;
|
||||
if (!CommandParser.GetEnum(p, msg, "Animal AI", ref ai)) return;
|
||||
|
||||
scope[id].AnimalAI = ai;
|
||||
Player.Message(p, "Animal AI for {0} set to: {1}",
|
||||
BlockName(scope, lvl, id), ai);
|
||||
OnPropsChanged(scope, lvl, id, true);
|
||||
}
|
||||
|
||||
static void SetDeathMessage(Player p, BlockProps[] scope, byte id, string msg) {
|
||||
@ -150,14 +165,16 @@ namespace MCGalaxy.Commands.World {
|
||||
Player.Message(p, "Death message for {0} set to: {1}",
|
||||
BlockName(scope, lvl, id), msg);
|
||||
}
|
||||
OnPropsChanged(scope, lvl, id);
|
||||
OnPropsChanged(scope, lvl, id, false);
|
||||
}
|
||||
|
||||
|
||||
static void OnPropsChanged(BlockProps[] scope, Level level, byte id) {
|
||||
static void OnPropsChanged(BlockProps[] scope, Level level, byte id, bool physics) {
|
||||
scope[id].Changed = true;
|
||||
|
||||
if (scope == Block.Props) {
|
||||
BlockBehaviour.InitCoreHandlers();
|
||||
if (physics) BlockBehaviour.InitCorePhysicsHandlers();
|
||||
BlockProps.Save("core", scope);
|
||||
} else if (scope == BlockDefinition.GlobalProps) {
|
||||
Level[] loaded = LevelInfo.Loaded.Items;
|
||||
@ -190,7 +207,7 @@ namespace MCGalaxy.Commands.World {
|
||||
Player.Message(p, "%H[scope] can be: %Score, global, level");
|
||||
|
||||
Player.Message(p, "%Hproperties: %Sportal, messageblock, rails, waterkills, " +
|
||||
"lavakills, door, tdoor, killer, deathmessage");
|
||||
"lavakills, door, tdoor, killer, deathmessage, animalai");
|
||||
Player.Message(p, "%HType %T/help blockprops [property] %Hfor more details");
|
||||
}
|
||||
|
||||
@ -214,6 +231,10 @@ namespace MCGalaxy.Commands.World {
|
||||
} else if (message.CaselessEq("deathmessage")) {
|
||||
Player.Message(p, "%HSets or removes the death message for this block");
|
||||
Player.Message(p, "%H Note: %S@p %His a placeholder for the player's name");
|
||||
} else if (message.CaselessEq("animalai")) {
|
||||
Player.Message(p, "%HSets the flying or swimming animal AI for this block.");
|
||||
string[] aiNames = Enum.GetNames(typeof(AnimalAI));
|
||||
Player.Message(p, "%H Types: &f{0}", aiNames.Join());
|
||||
} else {
|
||||
Player.Message(p, "&cUnrecognised property \"{0}\"", message);
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user