1
0
mirror of https://github.com/SquidDev-CC/CC-Tweaked synced 2025-01-26 17:06:54 +00:00

Cache a turtle's fake player

Player construction can get a little expensive, and this is exacerbated
by Sponge. We now cache a turtle's fake player (updating the position
every time it is requested) in order to reduce this overhead.
This commit is contained in:
SquidDev 2018-07-08 15:21:42 +01:00
parent 0ce6f34a09
commit 45a189e834
5 changed files with 44 additions and 23 deletions

View File

@ -128,6 +128,8 @@ public class TurtleBrain implements ITurtleAccess
private int m_animationProgress; private int m_animationProgress;
private int m_lastAnimationProgress; private int m_lastAnimationProgress;
TurtlePlayer m_cachedPlayer;
public TurtleBrain( TileTurtle turtle ) public TurtleBrain( TileTurtle turtle )
{ {
m_owner = turtle; m_owner = turtle;

View File

@ -180,12 +180,12 @@ public class TurtlePlaceCommand implements ITurtleCommand
public static TurtlePlayer createPlayer( ITurtleAccess turtle, BlockPos position, EnumFacing direction ) public static TurtlePlayer createPlayer( ITurtleAccess turtle, BlockPos position, EnumFacing direction )
{ {
TurtlePlayer turtlePlayer = new TurtlePlayer( turtle ); TurtlePlayer turtlePlayer = TurtlePlayer.get( turtle );
orientPlayer( turtle, turtlePlayer, position, direction ); orientPlayer( turtle, turtlePlayer, position, direction );
return turtlePlayer; return turtlePlayer;
} }
public static void orientPlayer( ITurtleAccess turtle, TurtlePlayer turtlePlayer, BlockPos position, EnumFacing direction ) private static void orientPlayer( ITurtleAccess turtle, TurtlePlayer turtlePlayer, BlockPos position, EnumFacing direction )
{ {
turtlePlayer.posX = position.getX() + 0.5; turtlePlayer.posX = position.getX() + 0.5;
turtlePlayer.posY = position.getY() + 0.5; turtlePlayer.posY = position.getY() + 0.5;

View File

@ -36,16 +36,31 @@ public class TurtlePlayer extends FakePlayer
"[ComputerCraft]" "[ComputerCraft]"
); );
/**
* Construct a TurtlePlayer which exists in the world
*
* @param world The world the player exists in
* @deprecated This is required by {@link Entity}.
*/
@Deprecated @Deprecated
public TurtlePlayer( World world ) public TurtlePlayer( World world )
{ {
super( (WorldServer) world, DEFAULT_PROFILE ); super( (WorldServer) world, DEFAULT_PROFILE );
} }
public TurtlePlayer( ITurtleAccess turtle ) private TurtlePlayer( ITurtleAccess turtle )
{ {
super( (WorldServer) turtle.getWorld(), getProfile( turtle.getOwningPlayer() )); super( (WorldServer) turtle.getWorld(), getProfile( turtle.getOwningPlayer() ) );
setState( turtle );
}
private static GameProfile getProfile( @Nullable GameProfile profile )
{
return profile != null && profile.isComplete() ? profile : DEFAULT_PROFILE;
}
private void setState( ITurtleAccess turtle )
{
BlockPos position = turtle.getPosition(); BlockPos position = turtle.getPosition();
posX = position.getX() + 0.5; posX = position.getX() + 0.5;
posY = position.getY() + 0.5; posY = position.getY() + 0.5;
@ -55,9 +70,23 @@ public class TurtlePlayer extends FakePlayer
rotationPitch = 0.0f; rotationPitch = 0.0f;
} }
private static GameProfile getProfile( @Nullable GameProfile profile ) public static TurtlePlayer get( ITurtleAccess access )
{ {
return profile != null && profile.isComplete() ? profile : DEFAULT_PROFILE; if( !(access instanceof TurtleBrain) ) return new TurtlePlayer( access );
TurtleBrain brain = (TurtleBrain) access;
TurtlePlayer player = brain.m_cachedPlayer;
if( player == null || player.getGameProfile() != getProfile( access.getOwningPlayer() )
|| player.getEntityWorld() != access.getWorld() )
{
player = brain.m_cachedPlayer = new TurtlePlayer( brain );
}
else
{
player.setState( access );
}
return player;
} }
public void loadInventory( @Nonnull ItemStack currentStack ) public void loadInventory( @Nonnull ItemStack currentStack )
@ -76,7 +105,7 @@ public class TurtlePlayer extends FakePlayer
// Store (or drop) anything else we found // Store (or drop) anything else we found
BlockPos dropPosition = turtle.getPosition(); BlockPos dropPosition = turtle.getPosition();
EnumFacing dropDirection = turtle.getDirection().getOpposite(); EnumFacing dropDirection = turtle.getDirection().getOpposite();
for( int i=0; i<inventory.getSizeInventory(); ++i ) for( int i = 0; i < inventory.getSizeInventory(); ++i )
{ {
ItemStack stack = inventory.getStackInSlot( i ); ItemStack stack = inventory.getStackInSlot( i );
if( !stack.isEmpty() ) if( !stack.isEmpty() )

View File

@ -118,7 +118,7 @@ public class TurtleInventoryCrafting extends InventoryCrafting
} }
// Do post-pickup stuff // Do post-pickup stuff
TurtlePlayer turtlePlayer = new TurtlePlayer( m_turtle ); TurtlePlayer turtlePlayer = TurtlePlayer.get( m_turtle );
result.onCrafting( world, turtlePlayer, numToCraft ); result.onCrafting( world, turtlePlayer, numToCraft );
results.add( result ); results.add( result );

View File

@ -29,12 +29,10 @@ import net.minecraft.item.Item;
import net.minecraft.item.ItemStack; import net.minecraft.item.ItemStack;
import net.minecraft.util.DamageSource; import net.minecraft.util.DamageSource;
import net.minecraft.util.EnumFacing; import net.minecraft.util.EnumFacing;
import net.minecraft.util.NonNullList;
import net.minecraft.util.ResourceLocation; import net.minecraft.util.ResourceLocation;
import net.minecraft.util.math.BlockPos; import net.minecraft.util.math.BlockPos;
import net.minecraft.util.math.Vec3d; import net.minecraft.util.math.Vec3d;
import net.minecraft.world.World; import net.minecraft.world.World;
import net.minecraftforge.common.ForgeHooks;
import net.minecraftforge.common.MinecraftForge; import net.minecraftforge.common.MinecraftForge;
import net.minecraftforge.event.ForgeEventFactory; import net.minecraftforge.event.ForgeEventFactory;
import net.minecraftforge.event.entity.player.AttackEntityEvent; import net.minecraftforge.event.entity.player.AttackEntityEvent;
@ -149,15 +147,6 @@ public class TurtleTool implements ITurtleUpgrade
return !block.isAir( state, world, pos ) && block != Blocks.BEDROCK && state.getBlockHardness( world, pos ) > -1.0F; return !block.isAir( state, world, pos ) && block != Blocks.BEDROCK && state.getBlockHardness( world, pos ) > -1.0F;
} }
protected boolean canHarvestBlock( ITurtleAccess turtleAccess, BlockPos pos )
{
World world = turtleAccess.getWorld();
Block block = world.getBlockState( pos ).getBlock();
TurtlePlayer turtlePlayer = new TurtlePlayer( turtleAccess );
turtlePlayer.loadInventory( m_item.copy() );
return ForgeHooks.canHarvestBlock( block, turtlePlayer, world, pos );
}
protected float getDamageMultiplier() protected float getDamageMultiplier()
{ {
return 3.0f; return 3.0f;
@ -287,8 +276,10 @@ public class TurtleTool implements ITurtleUpgrade
return TurtleCommandResult.failure( digEvent.getFailureMessage() ); return TurtleCommandResult.failure( digEvent.getFailureMessage() );
} }
IBlockState previousState = world.getBlockState( newPosition );
// Consume the items the block drops // Consume the items the block drops
if( canHarvestBlock( turtle, newPosition ) ) if( previousState.getBlock().canHarvestBlock( world, newPosition, turtlePlayer ) )
{ {
List<ItemStack> items = getBlockDropped( world, newPosition, turtlePlayer ); List<ItemStack> items = getBlockDropped( world, newPosition, turtlePlayer );
if( items != null && items.size() > 0 ) if( items != null && items.size() > 0 )
@ -306,7 +297,6 @@ public class TurtleTool implements ITurtleUpgrade
} }
// Destroy the block // Destroy the block
IBlockState previousState = world.getBlockState( newPosition );
world.playEvent(2001, newPosition, Block.getStateId(previousState)); world.playEvent(2001, newPosition, Block.getStateId(previousState));
world.setBlockToAir( newPosition ); world.setBlockToAir( newPosition );