2014-11-14 12:02:52 +01:00
|
|
|
/*
|
|
|
|
* This file is part of Applied Energistics 2.
|
2015-05-16 20:48:32 +02:00
|
|
|
* Copyright (c) 2013 - 2015, AlgorithmX2, All rights reserved.
|
2014-11-14 12:02:52 +01:00
|
|
|
*
|
|
|
|
* Applied Energistics 2 is free software: you can redistribute it and/or modify
|
|
|
|
* it under the terms of the GNU Lesser General Public License as published by
|
|
|
|
* the Free Software Foundation, either version 3 of the License, or
|
|
|
|
* (at your option) any later version.
|
|
|
|
*
|
|
|
|
* Applied Energistics 2 is distributed in the hope that it will be useful,
|
|
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
|
|
* GNU Lesser General Public License for more details.
|
|
|
|
*
|
|
|
|
* You should have received a copy of the GNU Lesser General Public License
|
|
|
|
* along with Applied Energistics 2. If not, see <http://www.gnu.org/licenses/lgpl>.
|
|
|
|
*/
|
|
|
|
|
2014-03-02 09:35:11 +01:00
|
|
|
package appeng.parts;
|
|
|
|
|
2015-01-03 02:53:14 +01:00
|
|
|
|
2014-03-02 09:35:11 +01:00
|
|
|
import java.util.LinkedList;
|
|
|
|
import java.util.List;
|
|
|
|
|
|
|
|
import net.minecraft.block.Block;
|
|
|
|
import net.minecraft.block.Block.SoundType;
|
2014-05-03 09:51:56 +02:00
|
|
|
import net.minecraft.client.Minecraft;
|
2014-03-02 09:35:11 +01:00
|
|
|
import net.minecraft.entity.player.EntityPlayer;
|
|
|
|
import net.minecraft.item.ItemBlock;
|
|
|
|
import net.minecraft.item.ItemStack;
|
|
|
|
import net.minecraft.tileentity.TileEntity;
|
2015-06-16 02:44:59 +02:00
|
|
|
import net.minecraft.util.BlockPos;
|
|
|
|
import net.minecraft.util.EnumFacing;
|
2014-03-02 09:35:11 +01:00
|
|
|
import net.minecraft.util.MovingObjectPosition;
|
2014-05-03 09:51:56 +02:00
|
|
|
import net.minecraft.util.Vec3;
|
2014-03-02 09:35:11 +01:00
|
|
|
import net.minecraft.world.World;
|
|
|
|
import net.minecraftforge.common.MinecraftForge;
|
|
|
|
import net.minecraftforge.event.entity.player.PlayerDestroyItemEvent;
|
|
|
|
import net.minecraftforge.event.entity.player.PlayerInteractEvent;
|
|
|
|
import net.minecraftforge.event.entity.player.PlayerInteractEvent.Action;
|
2015-06-16 02:44:59 +02:00
|
|
|
import net.minecraftforge.fml.common.eventhandler.SubscribeEvent;
|
|
|
|
import net.minecraftforge.fml.common.gameevent.TickEvent;
|
2014-03-02 09:35:11 +01:00
|
|
|
import appeng.api.AEApi;
|
2015-01-03 02:53:14 +01:00
|
|
|
import appeng.api.definitions.IBlockDefinition;
|
|
|
|
import appeng.api.definitions.IItems;
|
2014-03-02 09:35:11 +01:00
|
|
|
import appeng.api.parts.IFacadePart;
|
|
|
|
import appeng.api.parts.IPartHost;
|
|
|
|
import appeng.api.parts.IPartItem;
|
|
|
|
import appeng.api.parts.PartItemStack;
|
|
|
|
import appeng.api.parts.SelectedPart;
|
2015-06-16 02:44:59 +02:00
|
|
|
import appeng.api.util.AEPartLocation;
|
2014-08-29 04:37:08 +02:00
|
|
|
import appeng.api.util.DimensionalCoord;
|
2014-08-03 06:53:34 +02:00
|
|
|
import appeng.core.CommonHelper;
|
2014-03-02 09:35:11 +01:00
|
|
|
import appeng.core.sync.network.NetworkHandler;
|
2014-05-26 01:32:16 +02:00
|
|
|
import appeng.core.sync.packets.PacketClick;
|
2014-03-02 09:35:11 +01:00
|
|
|
import appeng.core.sync.packets.PacketPartPlacement;
|
|
|
|
import appeng.facade.IFacadeItem;
|
2015-05-16 20:48:32 +02:00
|
|
|
import appeng.integration.IntegrationRegistry;
|
2014-07-24 00:26:23 +02:00
|
|
|
import appeng.integration.IntegrationType;
|
2014-03-02 09:35:11 +01:00
|
|
|
import appeng.integration.abstraction.IBC;
|
|
|
|
import appeng.integration.abstraction.IFMP;
|
|
|
|
import appeng.util.LookDirection;
|
|
|
|
import appeng.util.Platform;
|
|
|
|
|
2015-06-16 02:44:59 +02:00
|
|
|
import com.google.common.base.Optional;
|
|
|
|
|
2015-01-03 02:53:14 +01:00
|
|
|
|
2014-03-02 09:35:11 +01:00
|
|
|
public class PartPlacement
|
|
|
|
{
|
|
|
|
|
2015-01-03 02:53:14 +01:00
|
|
|
public static float eyeHeight = 0.0f;
|
2014-09-29 09:54:34 +02:00
|
|
|
private final ThreadLocal<Object> placing = new ThreadLocal<Object>();
|
2014-08-01 02:43:44 +02:00
|
|
|
private boolean wasCanceled = false;
|
|
|
|
|
2015-06-16 02:44:59 +02:00
|
|
|
public static boolean place( ItemStack held, BlockPos pos, EnumFacing side, EntityPlayer player, World world, PlaceType pass, int depth )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2015-04-03 08:54:31 +02:00
|
|
|
if( depth > 3 )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2014-03-02 09:35:11 +01:00
|
|
|
return false;
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2014-03-02 09:35:11 +01:00
|
|
|
|
2015-06-16 02:44:59 +02:00
|
|
|
if( held != null && Platform.isWrench( player, held, pos ) && player.isSneaking() )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2015-06-16 02:44:59 +02:00
|
|
|
if( !Platform.hasPermissions( new DimensionalCoord( world, pos ), player ) )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2014-08-29 04:37:08 +02:00
|
|
|
return false;
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2014-08-29 04:37:08 +02:00
|
|
|
|
2015-06-16 02:44:59 +02:00
|
|
|
Block block = world.getBlockState( pos ).getBlock();
|
|
|
|
TileEntity tile = world.getTileEntity( pos );
|
2014-03-02 09:35:11 +01:00
|
|
|
IPartHost host = null;
|
|
|
|
|
2015-04-03 08:54:31 +02:00
|
|
|
if( tile instanceof IPartHost )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2014-03-02 09:35:11 +01:00
|
|
|
host = (IPartHost) tile;
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2014-03-02 09:35:11 +01:00
|
|
|
|
2015-04-03 08:54:31 +02:00
|
|
|
if( host != null )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2015-04-03 08:54:31 +02:00
|
|
|
if( !world.isRemote )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2014-08-29 04:37:08 +02:00
|
|
|
LookDirection dir = Platform.getPlayerRay( player, getEyeOffset( player ) );
|
2015-06-16 02:44:59 +02:00
|
|
|
MovingObjectPosition mop = block.collisionRayTrace( world, pos, dir.a, dir.b );
|
2015-04-03 08:54:31 +02:00
|
|
|
if( mop != null )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2014-09-28 22:20:14 +02:00
|
|
|
List<ItemStack> is = new LinkedList<ItemStack>();
|
2015-06-16 02:44:59 +02:00
|
|
|
SelectedPart sp = selectPart( player, host, mop.hitVec.addVector( -mop.getBlockPos().getX(), -mop.getBlockPos().getY(), -mop.getBlockPos().getZ() ) );
|
2014-03-02 09:35:11 +01:00
|
|
|
|
2015-04-03 08:54:31 +02:00
|
|
|
if( sp.part != null )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
|
|
|
is.add( sp.part.getItemStack( PartItemStack.Wrench ) );
|
|
|
|
sp.part.getDrops( is, true );
|
|
|
|
host.removePart( sp.side, false );
|
|
|
|
}
|
|
|
|
|
2015-04-03 08:54:31 +02:00
|
|
|
if( sp.facade != null )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
|
|
|
is.add( sp.facade.getItemStack() );
|
|
|
|
host.getFacadeContainer().removeFacade( host, sp.side );
|
2015-06-16 02:44:59 +02:00
|
|
|
Platform.notifyBlocksOfNeighbors( world, pos );
|
2014-03-02 09:35:11 +01:00
|
|
|
}
|
|
|
|
|
2015-04-03 08:54:31 +02:00
|
|
|
if( host.isEmpty() )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2014-04-10 22:01:04 +02:00
|
|
|
host.cleanup();
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2014-03-02 09:35:11 +01:00
|
|
|
|
2015-04-03 08:54:31 +02:00
|
|
|
if( !is.isEmpty() )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2015-06-16 02:44:59 +02:00
|
|
|
Platform.spawnDrops( world, pos, is );
|
2014-03-02 09:35:11 +01:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
player.swingItem();
|
2015-06-16 02:44:59 +02:00
|
|
|
NetworkHandler.instance.sendToServer( new PacketPartPlacement( pos, side, getEyeOffset( player ) ) );
|
2014-03-02 09:35:11 +01:00
|
|
|
}
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
2015-06-16 02:44:59 +02:00
|
|
|
TileEntity tile = world.getTileEntity( pos );
|
2014-03-02 09:35:11 +01:00
|
|
|
IPartHost host = null;
|
|
|
|
|
2015-04-03 08:54:31 +02:00
|
|
|
if( tile instanceof IPartHost )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2014-03-02 09:35:11 +01:00
|
|
|
host = (IPartHost) tile;
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2014-03-02 09:35:11 +01:00
|
|
|
|
2015-04-03 08:54:31 +02:00
|
|
|
if( held != null )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2015-06-16 02:44:59 +02:00
|
|
|
IFacadePart fp = isFacade( held, AEPartLocation.fromFacing( side ) );
|
2015-04-03 08:54:31 +02:00
|
|
|
if( fp != null )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2015-04-03 08:54:31 +02:00
|
|
|
if( host != null )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2015-04-03 08:54:31 +02:00
|
|
|
if( !world.isRemote )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2015-06-16 02:44:59 +02:00
|
|
|
if( host.getPart( AEPartLocation.INTERNAL ) == null )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2014-03-02 09:35:11 +01:00
|
|
|
return false;
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2014-03-02 09:35:11 +01:00
|
|
|
|
2015-06-16 02:44:59 +02:00
|
|
|
if( host.canAddPart( held, AEPartLocation.fromFacing( side ) ) )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2015-04-03 08:54:31 +02:00
|
|
|
if( host.getFacadeContainer().addFacade( fp ) )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2014-04-20 06:35:48 +02:00
|
|
|
host.markForUpdate();
|
2015-04-03 08:54:31 +02:00
|
|
|
if( !player.capabilities.isCreativeMode )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2014-04-20 06:35:48 +02:00
|
|
|
held.stackSize--;
|
2015-04-03 08:54:31 +02:00
|
|
|
if( held.stackSize == 0 )
|
2014-04-20 06:35:48 +02:00
|
|
|
{
|
|
|
|
player.inventory.mainInventory[player.inventory.currentItem] = null;
|
|
|
|
MinecraftForge.EVENT_BUS.post( new PlayerDestroyItemEvent( player, held ) );
|
|
|
|
}
|
2014-03-02 09:35:11 +01:00
|
|
|
}
|
2014-04-20 06:35:48 +02:00
|
|
|
return true;
|
2014-03-02 09:35:11 +01:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
player.swingItem();
|
2015-06-16 02:44:59 +02:00
|
|
|
NetworkHandler.instance.sendToServer( new PacketPartPlacement( pos, side, getEyeOffset( player ) ) );
|
2014-10-04 08:08:28 +02:00
|
|
|
return true;
|
2014-03-02 09:35:11 +01:00
|
|
|
}
|
|
|
|
}
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2015-06-16 02:44:59 +02:00
|
|
|
// TODO: IFMP INTEGRATION
|
|
|
|
// TODO IIMMIBISMICROBLOCKS INTEGRATION
|
|
|
|
|
|
|
|
/*
|
2015-05-16 20:48:32 +02:00
|
|
|
if( host == null && tile != null && IntegrationRegistry.INSTANCE.isEnabled( IntegrationType.FMP ) )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2015-05-16 20:48:32 +02:00
|
|
|
host = ( (IFMP) IntegrationRegistry.INSTANCE.getInstance( IntegrationType.FMP ) ).getOrCreateHost( tile );
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2014-03-02 09:35:11 +01:00
|
|
|
|
2015-05-16 20:48:32 +02:00
|
|
|
if( host == null && tile != null && IntegrationRegistry.INSTANCE.isEnabled( IntegrationType.ImmibisMicroblocks ) )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2015-05-16 20:48:32 +02:00
|
|
|
host = ( (IImmibisMicroblocks) IntegrationRegistry.INSTANCE.getInstance( IntegrationType.ImmibisMicroblocks ) ).getOrCreateHost( player, face, tile );
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2015-06-16 02:44:59 +02:00
|
|
|
*/
|
|
|
|
|
2014-03-02 09:35:11 +01:00
|
|
|
// if ( held == null )
|
|
|
|
{
|
2015-06-16 02:44:59 +02:00
|
|
|
Block block = world.getBlockState( pos ).getBlock();
|
2015-04-03 08:54:31 +02:00
|
|
|
if( host != null && player.isSneaking() && block != null )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2014-08-29 04:37:08 +02:00
|
|
|
LookDirection dir = Platform.getPlayerRay( player, getEyeOffset( player ) );
|
2015-06-16 02:44:59 +02:00
|
|
|
MovingObjectPosition mop = block.collisionRayTrace( world, pos, dir.a, dir.b );
|
2015-04-03 08:54:31 +02:00
|
|
|
if( mop != null )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2015-06-16 02:44:59 +02:00
|
|
|
mop.hitVec = mop.hitVec.addVector( -mop.getBlockPos().getX(), -mop.getBlockPos().getY(), -mop.getBlockPos().getZ() );
|
2014-08-03 06:53:34 +02:00
|
|
|
SelectedPart sPart = selectPart( player, host, mop.hitVec );
|
2015-04-03 08:54:31 +02:00
|
|
|
if( sPart != null && sPart.part != null )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2015-04-03 08:54:31 +02:00
|
|
|
if( sPart.part.onShiftActivate( player, mop.hitVec ) )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2015-04-03 08:54:31 +02:00
|
|
|
if( world.isRemote )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2015-06-16 02:44:59 +02:00
|
|
|
NetworkHandler.instance.sendToServer( new PacketPartPlacement( pos, side, getEyeOffset( player ) ) );
|
2014-03-02 09:35:11 +01:00
|
|
|
}
|
|
|
|
return true;
|
|
|
|
}
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2014-03-02 09:35:11 +01:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2015-04-03 08:54:31 +02:00
|
|
|
if( held == null || !( held.getItem() instanceof IPartItem ) )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2014-03-02 09:35:11 +01:00
|
|
|
return false;
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2014-03-02 09:35:11 +01:00
|
|
|
|
2015-06-16 02:44:59 +02:00
|
|
|
BlockPos te_pos = pos;
|
2014-03-02 09:35:11 +01:00
|
|
|
|
2015-01-03 02:53:14 +01:00
|
|
|
final IBlockDefinition multiPart = AEApi.instance().definitions().blocks().multiPart();
|
2015-04-03 08:54:31 +02:00
|
|
|
if( host == null && pass == PlaceType.PLACE_ITEM )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2015-06-16 02:44:59 +02:00
|
|
|
EnumFacing offset = null;
|
2014-03-02 09:35:11 +01:00
|
|
|
|
2015-06-16 02:44:59 +02:00
|
|
|
Block blkID = world.getBlockState( pos ).getBlock();
|
|
|
|
if( blkID != null && !blkID.isReplaceable( world, pos ) )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
|
|
|
offset = side;
|
2015-04-03 08:54:31 +02:00
|
|
|
if( Platform.isServer() )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2014-03-02 09:35:11 +01:00
|
|
|
side = side.getOpposite();
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2014-03-02 09:35:11 +01:00
|
|
|
}
|
|
|
|
|
2015-06-16 02:44:59 +02:00
|
|
|
te_pos = offset == null ? pos : pos.offset( offset );
|
2014-03-02 09:35:11 +01:00
|
|
|
|
2015-06-16 02:44:59 +02:00
|
|
|
tile = world.getTileEntity( te_pos );
|
2015-04-03 08:54:31 +02:00
|
|
|
if( tile instanceof IPartHost )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2014-03-02 09:35:11 +01:00
|
|
|
host = (IPartHost) tile;
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2014-03-02 09:35:11 +01:00
|
|
|
|
2015-06-16 02:44:59 +02:00
|
|
|
// TODO: IFMP INTEGRATION
|
|
|
|
// TODO IIMMIBISMICROBLOCKS INTEGRATION
|
|
|
|
|
|
|
|
/*
|
2015-05-16 20:48:32 +02:00
|
|
|
if( host == null && tile != null && IntegrationRegistry.INSTANCE.isEnabled( IntegrationType.FMP ) )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2015-05-16 20:48:32 +02:00
|
|
|
host = ( (IFMP) IntegrationRegistry.INSTANCE.getInstance( IntegrationType.FMP ) ).getOrCreateHost( tile );
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2014-03-02 09:35:11 +01:00
|
|
|
|
2015-05-16 20:48:32 +02:00
|
|
|
if( host == null && tile != null && IntegrationRegistry.INSTANCE.isEnabled( IntegrationType.ImmibisMicroblocks ) )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2015-06-16 02:44:59 +02:00
|
|
|
host = ( (IImmibisMicroblocks) IntegrationRegistry.INSTANCE.getInstance( IntegrationType.ImmibisMicroblocks ) ).getOrCreateHost( player, side, tile );
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2015-06-16 02:44:59 +02:00
|
|
|
*/
|
|
|
|
|
2015-01-03 02:53:14 +01:00
|
|
|
final Optional<ItemStack> maybeMultiPartStack = multiPart.maybeStack( 1 );
|
|
|
|
final Optional<Block> maybeMultiPartBlock = multiPart.maybeBlock();
|
|
|
|
final Optional<ItemBlock> maybeMultiPartItemBlock = multiPart.maybeItemBlock();
|
2014-08-30 04:34:33 +02:00
|
|
|
|
2015-01-03 02:53:14 +01:00
|
|
|
final boolean hostIsNotPresent = host == null;
|
|
|
|
final boolean multiPartPresent = maybeMultiPartBlock.isPresent() && maybeMultiPartStack.isPresent() && maybeMultiPartItemBlock.isPresent();
|
2015-06-16 02:44:59 +02:00
|
|
|
final boolean canMultiPartBePlaced = maybeMultiPartBlock.get().canPlaceBlockAt( world, te_pos );
|
2015-01-03 02:53:14 +01:00
|
|
|
|
2015-06-16 02:44:59 +02:00
|
|
|
if( hostIsNotPresent && multiPartPresent && canMultiPartBePlaced && maybeMultiPartItemBlock.get().placeBlockAt( maybeMultiPartStack.get(), player, world, te_pos, side, 0.5f, 0.5f, 0.5f, maybeMultiPartBlock.get().getDefaultState() ) )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2015-04-03 08:54:31 +02:00
|
|
|
if( !world.isRemote )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2015-06-16 02:44:59 +02:00
|
|
|
tile = world.getTileEntity( te_pos );
|
2014-03-02 09:35:11 +01:00
|
|
|
|
2015-04-03 08:54:31 +02:00
|
|
|
if( tile instanceof IPartHost )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2014-03-02 09:35:11 +01:00
|
|
|
host = (IPartHost) tile;
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2014-03-02 09:35:11 +01:00
|
|
|
|
|
|
|
pass = PlaceType.INTERACT_SECOND_PASS;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
player.swingItem();
|
2015-06-16 02:44:59 +02:00
|
|
|
NetworkHandler.instance.sendToServer( new PacketPartPlacement( pos, side, getEyeOffset( player ) ) );
|
2014-03-02 09:35:11 +01:00
|
|
|
return true;
|
|
|
|
}
|
|
|
|
}
|
2015-06-16 02:44:59 +02:00
|
|
|
else if( host != null && !host.canAddPart( held, AEPartLocation.fromFacing( side ) ) )
|
2015-01-03 02:53:14 +01:00
|
|
|
{
|
2014-03-02 09:35:11 +01:00
|
|
|
return false;
|
2015-01-03 02:53:14 +01:00
|
|
|
}
|
2014-03-02 09:35:11 +01:00
|
|
|
}
|
|
|
|
|
2015-04-03 08:54:31 +02:00
|
|
|
if( host == null )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2014-03-02 09:35:11 +01:00
|
|
|
return false;
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2014-03-02 09:35:11 +01:00
|
|
|
|
2015-06-16 02:44:59 +02:00
|
|
|
if( !host.canAddPart( held, AEPartLocation.fromFacing( side ) ) )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2015-04-03 08:54:31 +02:00
|
|
|
if( pass == PlaceType.INTERACT_FIRST_PASS || pass == PlaceType.PLACE_ITEM )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2015-06-16 02:44:59 +02:00
|
|
|
te_pos = pos.offset( side );
|
|
|
|
|
|
|
|
Block blkID = world.getBlockState( te_pos ).getBlock();
|
|
|
|
tile = world.getTileEntity( te_pos );
|
2014-03-02 09:35:11 +01:00
|
|
|
|
2015-05-16 20:48:32 +02:00
|
|
|
if( tile != null && IntegrationRegistry.INSTANCE.isEnabled( IntegrationType.FMP ) )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2015-05-16 20:48:32 +02:00
|
|
|
host = ( (IFMP) IntegrationRegistry.INSTANCE.getInstance( IntegrationType.FMP ) ).getOrCreateHost( tile );
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2014-03-02 09:35:11 +01:00
|
|
|
|
2015-06-16 02:44:59 +02:00
|
|
|
if( ( blkID == null || blkID.isReplaceable( world, te_pos ) || host != null ) ) ///&& side != AEPartLocation.INTERNAL )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2015-06-16 02:44:59 +02:00
|
|
|
return place( held, te_pos, side.getOpposite(), player, world, pass == PlaceType.INTERACT_FIRST_PASS ? PlaceType.INTERACT_SECOND_PASS : PlaceType.PLACE_ITEM, depth + 1 );
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2014-03-02 09:35:11 +01:00
|
|
|
}
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
2015-04-03 08:54:31 +02:00
|
|
|
if( !world.isRemote )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2015-06-16 02:44:59 +02:00
|
|
|
Block block = world.getBlockState( pos ).getBlock();
|
2014-08-29 04:37:08 +02:00
|
|
|
LookDirection dir = Platform.getPlayerRay( player, getEyeOffset( player ) );
|
2015-06-16 02:44:59 +02:00
|
|
|
MovingObjectPosition mop = block.collisionRayTrace( world, pos, dir.a, dir.b );
|
2015-04-03 08:54:31 +02:00
|
|
|
if( mop != null )
|
2014-03-15 07:58:21 +01:00
|
|
|
{
|
2015-06-16 02:44:59 +02:00
|
|
|
SelectedPart sp = selectPart( player, host, mop.hitVec.addVector( -mop.getBlockPos().getX(), -mop.getBlockPos().getY(), -mop.getBlockPos().getZ() ) );
|
2014-03-15 07:58:21 +01:00
|
|
|
|
2015-04-03 08:54:31 +02:00
|
|
|
if( sp.part != null )
|
2014-03-15 07:58:21 +01:00
|
|
|
{
|
2015-04-03 08:54:31 +02:00
|
|
|
if( !player.isSneaking() && sp.part.onActivate( player, mop.hitVec ) )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2014-03-15 07:58:21 +01:00
|
|
|
return false;
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2014-03-15 07:58:21 +01:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2014-08-29 04:37:08 +02:00
|
|
|
DimensionalCoord dc = host.getLocation();
|
2015-04-03 08:54:31 +02:00
|
|
|
if( !Platform.hasPermissions( dc, player ) )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2014-08-29 04:37:08 +02:00
|
|
|
return false;
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2014-08-29 04:37:08 +02:00
|
|
|
|
2015-06-16 02:44:59 +02:00
|
|
|
AEPartLocation mySide = host.addPart( held, AEPartLocation.fromFacing( side ), player );
|
2015-04-03 08:54:31 +02:00
|
|
|
if( mySide != null )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2015-04-03 08:54:31 +02:00
|
|
|
for( Block multiPartBlock : multiPart.maybeBlock().asSet() )
|
2015-01-03 02:53:14 +01:00
|
|
|
{
|
|
|
|
final SoundType ss = multiPartBlock.stepSound;
|
2014-03-02 09:35:11 +01:00
|
|
|
|
2015-06-16 02:44:59 +02:00
|
|
|
world.playSoundEffect( 0.5 + pos.getX(), 0.5 + pos.getY(), 0.5 + pos.getZ(), ss.getPlaceSound(), ( ss.getVolume() + 1.0F ) / 2.0F, ss.getFrequency() * 0.8F );
|
2015-01-03 02:53:14 +01:00
|
|
|
}
|
2014-03-02 09:35:11 +01:00
|
|
|
|
2015-04-03 08:54:31 +02:00
|
|
|
if( !player.capabilities.isCreativeMode )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
|
|
|
held.stackSize--;
|
2015-04-03 08:54:31 +02:00
|
|
|
if( held.stackSize == 0 )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
|
|
|
player.inventory.mainInventory[player.inventory.currentItem] = null;
|
|
|
|
MinecraftForge.EVENT_BUS.post( new PlayerDestroyItemEvent( player, held ) );
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
player.swingItem();
|
2015-06-16 02:44:59 +02:00
|
|
|
NetworkHandler.instance.sendToServer( new PacketPartPlacement( pos, side, getEyeOffset( player ) ) );
|
2014-03-02 09:35:11 +01:00
|
|
|
}
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
2015-01-03 02:53:14 +01:00
|
|
|
private static float getEyeOffset( EntityPlayer p )
|
2014-08-18 23:12:45 +02:00
|
|
|
{
|
2015-04-03 08:54:31 +02:00
|
|
|
if( p.worldObj.isRemote )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2014-08-18 23:12:45 +02:00
|
|
|
return Platform.getEyeOffset( p );
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2014-08-29 04:37:08 +02:00
|
|
|
|
2014-08-18 23:12:45 +02:00
|
|
|
return eyeHeight;
|
|
|
|
}
|
|
|
|
|
2015-01-03 02:53:14 +01:00
|
|
|
private static SelectedPart selectPart( EntityPlayer player, IPartHost host, Vec3 pos )
|
2014-08-03 06:53:34 +02:00
|
|
|
{
|
|
|
|
CommonHelper.proxy.updateRenderMode( player );
|
|
|
|
SelectedPart sp = host.selectPart( pos );
|
|
|
|
CommonHelper.proxy.updateRenderMode( null );
|
|
|
|
|
|
|
|
return sp;
|
|
|
|
}
|
|
|
|
|
2015-06-16 02:44:59 +02:00
|
|
|
public static IFacadePart isFacade( ItemStack held, AEPartLocation side )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2015-04-03 08:54:31 +02:00
|
|
|
if( held.getItem() instanceof IFacadeItem )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2015-01-03 02:53:14 +01:00
|
|
|
return ( (IFacadeItem) held.getItem() ).createPartFromItemStack( held, side );
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2014-05-04 21:54:07 +02:00
|
|
|
|
2015-05-16 20:48:32 +02:00
|
|
|
if( IntegrationRegistry.INSTANCE.isEnabled( IntegrationType.BC ) )
|
2014-03-02 09:35:11 +01:00
|
|
|
{
|
2015-05-16 20:48:32 +02:00
|
|
|
IBC bc = (IBC) IntegrationRegistry.INSTANCE.getInstance( IntegrationType.BC );
|
2015-04-03 08:54:31 +02:00
|
|
|
if( bc.isFacade( held ) )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2014-03-02 09:35:11 +01:00
|
|
|
return bc.createFacadePart( held, side );
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2014-03-02 09:35:11 +01:00
|
|
|
}
|
2014-05-04 21:54:07 +02:00
|
|
|
|
2014-03-02 09:35:11 +01:00
|
|
|
return null;
|
|
|
|
}
|
|
|
|
|
2015-01-03 02:53:14 +01:00
|
|
|
@SubscribeEvent
|
|
|
|
public void playerInteract( TickEvent.ClientTickEvent event )
|
|
|
|
{
|
|
|
|
this.wasCanceled = false;
|
|
|
|
}
|
|
|
|
|
|
|
|
@SubscribeEvent
|
|
|
|
public void playerInteract( PlayerInteractEvent event )
|
|
|
|
{
|
2015-04-03 08:54:31 +02:00
|
|
|
if( event.action == Action.RIGHT_CLICK_AIR && event.entityPlayer.worldObj.isRemote )
|
2015-01-03 02:53:14 +01:00
|
|
|
{
|
|
|
|
// re-check to see if this event was already channeled, cause these two events are really stupid...
|
|
|
|
MovingObjectPosition mop = Platform.rayTrace( event.entityPlayer, true, false );
|
|
|
|
Minecraft mc = Minecraft.getMinecraft();
|
|
|
|
|
|
|
|
float f = 1.0F;
|
|
|
|
double d0 = mc.playerController.getBlockReachDistance();
|
2015-06-16 02:44:59 +02:00
|
|
|
Vec3 vec3 = mc.getRenderViewEntity().getPositionEyes( f );
|
2015-01-03 02:53:14 +01:00
|
|
|
|
2015-04-03 08:54:31 +02:00
|
|
|
if( mop != null && mop.hitVec.distanceTo( vec3 ) < d0 )
|
2015-01-03 02:53:14 +01:00
|
|
|
{
|
|
|
|
World w = event.entity.worldObj;
|
2015-06-16 02:44:59 +02:00
|
|
|
TileEntity te = w.getTileEntity( mop.getBlockPos() );
|
2015-04-03 08:54:31 +02:00
|
|
|
if( te instanceof IPartHost && this.wasCanceled )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2015-01-03 02:53:14 +01:00
|
|
|
event.setCanceled( true );
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2015-01-03 02:53:14 +01:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
ItemStack held = event.entityPlayer.getHeldItem();
|
|
|
|
final IItems items = AEApi.instance().definitions().items();
|
|
|
|
|
|
|
|
boolean supportedItem = items.memoryCard().isSameAs( held );
|
|
|
|
supportedItem |= items.colorApplicator().isSameAs( held );
|
|
|
|
|
2015-04-03 08:54:31 +02:00
|
|
|
if( event.entityPlayer.isSneaking() && held != null && supportedItem )
|
2015-01-03 02:53:14 +01:00
|
|
|
{
|
2015-06-16 02:44:59 +02:00
|
|
|
NetworkHandler.instance.sendToServer( new PacketClick( event.pos, event.face, 0, 0, 0 ) );
|
2015-01-03 02:53:14 +01:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2015-04-03 08:54:31 +02:00
|
|
|
else if( event.action == Action.RIGHT_CLICK_BLOCK && event.entityPlayer.worldObj.isRemote )
|
2015-01-03 02:53:14 +01:00
|
|
|
{
|
2015-04-03 08:54:31 +02:00
|
|
|
if( this.placing.get() != null )
|
2015-04-29 02:30:53 +02:00
|
|
|
{
|
2015-01-03 02:53:14 +01:00
|
|
|
return;
|
2015-04-29 02:30:53 +02:00
|
|
|
}
|
2015-01-03 02:53:14 +01:00
|
|
|
|
|
|
|
this.placing.set( event );
|
|
|
|
|
|
|
|
ItemStack held = event.entityPlayer.getHeldItem();
|
2015-06-16 02:44:59 +02:00
|
|
|
if( place( held, event.pos, event.face, event.entityPlayer, event.entityPlayer.worldObj, PlaceType.INTERACT_FIRST_PASS, 0 ) )
|
2015-01-03 02:53:14 +01:00
|
|
|
{
|
|
|
|
event.setCanceled( true );
|
|
|
|
this.wasCanceled = true;
|
|
|
|
}
|
|
|
|
|
|
|
|
this.placing.set( null );
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
public enum PlaceType
|
|
|
|
{
|
|
|
|
PLACE_ITEM, INTERACT_FIRST_PASS, INTERACT_SECOND_PASS
|
|
|
|
}
|
2013-12-27 23:59:59 +01:00
|
|
|
}
|