Add item repository and leaves logic

This commit is contained in:
Drew DeVault 2015-02-01 14:59:02 -07:00
parent e3051a673c
commit 4df341e7d6
9 changed files with 120 additions and 1 deletions

View File

@ -0,0 +1,21 @@
using System;
namespace TrueCraft.API.Logic
{
/// <summary>
/// Providers item providers for a server.
/// </summary>
public interface IItemRepository
{
/// <summary>
/// Gets this repository's item provider for the specified item ID. This may return null
/// if the item ID in question has no corresponding block provider.
/// </summary>
IItemProvider GetItemProvider(short id);
/// <summary>
/// Registers a new item provider. This overrides any existing item providers that use the
/// same item ID.
/// </summary>
void RegisterItemProvider(IItemProvider provider);
}
}

View File

@ -24,6 +24,7 @@ namespace TrueCraft.API.Server
IList<IWorld> Worlds { get; }
IEventScheduler Scheduler { get; }
IBlockRepository BlockRepository { get; }
IItemRepository ItemRepository { get; }
void Start(IPEndPoint endPoint);
void RegisterPacketHandler(byte packetId, PacketHandler handler);

View File

@ -83,6 +83,7 @@
<Compile Include="Entities\IAABBEntity.cs" />
<Compile Include="Entities\IBlockPhysicsProvider.cs" />
<Compile Include="Entities\IPhysicsEntity.cs" />
<Compile Include="Logic\IItemRepository.cs" />
</ItemGroup>
<Import Project="$(MSBuildBinPath)\Microsoft.CSharp.targets" />
<ItemGroup />

View File

@ -1,5 +1,8 @@
using System;
using TrueCraft.API.Logic;
using TrueCraft.API;
using TrueCraft.API.World;
using TrueCraft.Core.Logic.Items;
namespace TrueCraft.Core.Logic.Blocks
{
@ -21,5 +24,10 @@ namespace TrueCraft.Core.Logic.Blocks
{
return new Tuple<int, int>(8, 4);
}
protected override ItemStack[] GetDrop(BlockDescriptor descriptor)
{
return new[] { new ItemStack(ClayItem.ItemID, 4) };
}
}
}

View File

@ -1,5 +1,7 @@
using System;
using TrueCraft.API.Logic;
using TrueCraft.API;
using TrueCraft.API.World;
namespace TrueCraft.Core.Logic.Blocks
{
@ -25,5 +27,13 @@ namespace TrueCraft.Core.Logic.Blocks
{
return new Tuple<int, int>(4, 3);
}
protected override ItemStack[] GetDrop(BlockDescriptor descriptor)
{
if (MathHelper.Random.Next(20) == 0) // 5% chance
return new[] { new ItemStack(SaplingBlock.BlockID, 1, descriptor.Metadata) };
else
return new ItemStack[0];
}
}
}

View File

@ -18,6 +18,7 @@ namespace TrueCraft.Handlers
var world = _client.World;
var position = new Coordinates3D(packet.X, packet.Y, packet.Z);
var descriptor = world.GetBlockData(position);
var provider = server.BlockRepository.GetBlockProvider(descriptor.ID);
switch (packet.PlayerAction)
{
case PlayerDiggingPacket.Action.DropItem:
@ -30,6 +31,8 @@ namespace TrueCraft.Handlers
if (c.KnownEntities.Contains(client.Entity))
c.QueuePacket(new AnimationPacket(client.Entity.EntityID, AnimationPacket.PlayerAnimation.SwingArm));
}
if (provider.Hardness == 0)
provider.BlockMined(descriptor, packet.Face, world, client);
break;
case PlayerDiggingPacket.Action.StopDigging:
foreach (var nearbyClient in server.Clients)
@ -38,7 +41,6 @@ namespace TrueCraft.Handlers
if (c.KnownEntities.Contains(client.Entity))
c.QueuePacket(new AnimationPacket(client.Entity.EntityID, AnimationPacket.PlayerAnimation.None));
}
var provider = server.BlockRepository.GetBlockProvider(descriptor.ID);
provider.BlockMined(descriptor, packet.Face, world, client);
break;
}

View File

@ -0,0 +1,71 @@
using System;
using TrueCraft.API.Logic;
using System.Collections.Generic;
using System.Linq;
using TrueCraft.API.Entities;
using TrueCraft.API;
using TrueCraft.API.World;
namespace TrueCraft
{
public class ItemRepository : IItemRepository
{
public ItemRepository()
{
ItemProviders = new List<IItemProvider>();
}
private readonly List<IItemProvider> ItemProviders = new List<IItemProvider>();
public IItemProvider GetItemProvider(short id)
{
int max = ItemProviders.Count - 1, min = 0;
while (max >= min)
{
int mid = (max - min / 2) + min;
if (ItemProviders[mid].ID == id)
return ItemProviders[mid];
else if(ItemProviders[mid].ID < id)
min = mid + 1;
else
max = min - 1;
}
return null;
}
public void RegisterItemProvider(IItemProvider provider)
{
int i;
for (i = ItemProviders.Count - 1; i >= 0; i--)
{
if (provider.ID == ItemProviders[i].ID)
{
ItemProviders[i] = provider; // Override
return;
}
if (ItemProviders[i].ID < provider.ID)
break;
}
ItemProviders.Insert(i + 1, provider);
}
internal void DiscoverItemProviders()
{
var providerTypes = new List<Type>();
foreach (var assembly in AppDomain.CurrentDomain.GetAssemblies())
{
foreach (var type in assembly.GetTypes().Where(t =>
typeof(IItemProvider).IsAssignableFrom(t) && !t.IsAbstract))
{
providerTypes.Add(type);
}
}
providerTypes.ForEach(t =>
{
var instance = (IItemProvider)Activator.CreateInstance(t);
RegisterItemProvider(instance);
});
}
}
}

View File

@ -27,6 +27,7 @@ namespace TrueCraft
public IList<IEntityManager> EntityManagers { get; private set; }
public IEventScheduler Scheduler { get; private set; }
public IBlockRepository BlockRepository { get; private set; }
public IItemRepository ItemRepository { get; private set; }
private Timer EnvironmentWorker;
private Thread NetworkWorker;
@ -49,6 +50,9 @@ namespace TrueCraft
var blockRepository = new BlockRepository();
blockRepository.DiscoverBlockProviders();
BlockRepository = blockRepository;
var itemRepository = new ItemRepository();
itemRepository.DiscoverItemProviders();
ItemRepository = itemRepository;
reader.RegisterCorePackets();
Handlers.PacketHandlers.RegisterHandlers(this);

View File

@ -54,6 +54,7 @@
<Compile Include="BlockRepository.cs" />
<Compile Include="Exceptions\PlayerDisconnectException.cs" />
<Compile Include="PhysicsEngine.cs" />
<Compile Include="ItemRepository.cs" />
</ItemGroup>
<Import Project="$(MSBuildBinPath)\Microsoft.CSharp.targets" />
<ItemGroup>