DIFF

actionbuildpartinstant.c


#ifdef DIAG_DEVELOPER
class ActionBuildPartInstantDebug : ActionInstantBase
{	
	void ActionBuildPartInstantDebug()
	{
		m_Text = "build part debug";
	}
	
	override bool HasTarget()
	{
		return true;
	}
	
	override void CreateConditionComponents()  
	{	
		m_ConditionItem = new CCINone();
		m_ConditionTarget = new CCTCursor();
	}
	
	override void OnActionInfoUpdate(PlayerBase player, ActionTarget target, ItemBase item)
	{
		ConstructionActionData cad = player.GetConstructionActionData();
		ConstructionPart part = cad.GetBuildPartInstantAtIndex(m_VariantID);
		if (part)
		{
			m_Text = "dbgBuild "+ part.GetName() + " - INSTANT";
			
			#ifdef DIAG_DEVELOPER
			if (DiagMenu.GetBool(DiagMenuIDs.BASEBUILDING_FULLDEBUG))
			{
				m_Text = "dbgBuild | part classname: " + part.GetPartName() + " - INSTANT";
			}
			#endif
		}
	}
	
	override void InitInfoData()
	{
		m_InfoData = new ActionInfoDataConstructionPossible();
	}
	
	override bool CanBeUsedLeaning()
	{
		return false;
	}
	
	override bool CanBeUsedInFreelook()
	{
		return false;
	}
	
	override bool ActionCondition(PlayerBase player, ActionTarget target, ItemBase item)
	{
		ConstructionActionData cad = player.GetConstructionActionData();
		if (cad.GetFastConstructionMode() != EConstructionDebugModes.INSTANT)
			return false;
		
		EntityAI ent;
		if (!Class.CastTo(ent,target.GetObject()))
			return false;
		
		if (player.IsPlacingLocal() || player.IsPlacingServer())
			return false;
		
		//Action not allowed if player has broken legs
		if (player.GetBrokenLegs() == eBrokenLegs.BROKEN_LEGS)
			return false;
		
		if (!ent.CanUseConstruction() || !ent.CanUseConstructionBuild())
			return false;
		
		if ((!GetGame().IsDedicatedServer()))
		{
			if (!PositioningCheck(player, target))
				return false;
			
			if (MiscGameplayFunctions.ComplexBuildCollideCheckClient(player, target, item, m_VariantID))
				return GatherInfoData(player,target,item);
			
			return false;
		}
		return true;
	}
	
	override void OnStartServer(ActionData action_data)
	{
		EntityAI ent = EntityAI.Cast(action_data.m_Target.GetObject());
		ConstructionBase construction = ConstructionBase.Cast(ent.GetConstructionBasic());
		
		string partName = BuildPartActionData.Cast(action_data).m_PartType;
		ConstructionPart part = construction.GetConstructionPart(partName);
		CollisionCheckData checkData = new CollisionCheckData();
		
		checkData.m_PartName = partName;
		checkData.m_AdditionalExcludes.Insert(action_data.m_Player);
		
		bool canBuild = construction.CanBuildPart(partName, action_data.m_MainItem, UseMainItem()); //TODO: do we need to check it here when ActionVariantManager already does it?
		#ifdef DIAG_DEVELOPER
		if (action_data.m_Player.GetConstructionActionData().GetFastConstructionMode())
			canBuild = true;
		#endif
		if (!construction.IsCollidingEx(checkData) && canBuild)
		{
			//build
			construction.BuildPartServerEx(action_data.m_Player, partName, AT_BUILD_PART);
		}
	}
	
	override ActionData CreateActionData()
	{
		BuildPartActionData action_data = new BuildPartActionData();
		return action_data;
	}
	
	override bool SetupAction(PlayerBase player, ActionTarget target, ItemBase item, out ActionData action_data, Param extra_data = NULL)
	{	
		if (super.SetupAction(player, target, item, action_data, extra_data))
		{
			if (!g_Game.IsDedicatedServer())
				ComposeBuildActionDataClient(player,target,item,action_data,extra_data);
			
			return true;
		}
		
		return false;
	}
	
	protected void ComposeBuildActionDataClient(PlayerBase player, ActionTarget target, ItemBase item, out ActionData action_data, Param extra_data = NULL)
	{
		ConstructionActionData cad = action_data.m_Player.GetConstructionActionData();
		ConstructionPart part = cad.GetBuildPartInstantAtIndex(m_VariantID);
		BuildPartActionData.Cast(action_data).m_PartType = part.GetPartName();
	}
	
	override void WriteToContext(ParamsWriteContext ctx, ActionData action_data)
	{
		super.WriteToContext(ctx, action_data);
		
		ctx.Write(BuildPartActionData.Cast(action_data).m_PartType);
	}
	
	override bool ReadFromContext(ParamsReadContext ctx, out ActionReciveData action_recive_data)
	{
		action_recive_data = new BuildPartActionReciveData();
		super.ReadFromContext(ctx, action_recive_data);
		
		string partType;
		if (ctx.Read(partType))
		{
			BuildPartActionReciveData.Cast(action_recive_data).m_PartType = partType;
			return true;
		}
		else
		{
			return false;
		}
	}
	
	override void HandleReciveData(ActionReciveData action_recive_data, ActionData action_data)
	{
		super.HandleReciveData(action_recive_data, action_data);
		
		BuildPartActionData.Cast(action_data).m_PartType = BuildPartActionReciveData.Cast(action_recive_data).m_PartType;
	}
	
	protected void ClearInfoData()
	{
		m_InfoData.m_InfoContextMask = 0;
	}
	
	protected bool GatherInfoData(PlayerBase player, ActionTarget target, ItemBase item)
	{
		ClearInfoData();
		
		ActionInfoDataConstructionPossible info = ActionInfoDataConstructionPossible.Cast(m_InfoData);
		ConstructionActionData cad = player.GetConstructionActionData();
		ConstructionPart part = cad.GetBuildPartInstantAtIndex(m_VariantID);
		info.SetConstructionPart(part);
		info.SetTool(item);
		
		info.m_InfoContextMask |= EConstructionInfoCategories.MATERIALS_PRESENCE; //material info should always be visible
		info.m_InfoContextMask |= EConstructionInfoCategories.TOOL_PRESENCE; //tools info should always be visible
		
		return info.CanDisplayInfo();
	}
	
	//! Can build from the inside only, if applicable
	protected bool PositioningCheck(PlayerBase player, ActionTarget target)
	{
		EntityAI ent = EntityAI.Cast(target.GetObject());
		BaseBuildingBase bbb = BaseBuildingBase.Cast(ent);
		ConstructionActionData cad = player.GetConstructionActionData();
		ConstructionPart part = GetTargetPart(cad);
		
		if (part)
		{
			ConstructionBase construction = ConstructionBase.Cast(ent.GetConstructionBasic());
			if (!ent.IsPlayerInsideEx(player, part.GetPartName()))
			{
				if (bbb && !bbb.MustBeBuiltFromOutside())
					return false;
				else if (!bbb)
					return false;
			}
			if (!construction.ConstructionDirectionCheck(player, part, EConstructionDirCheckType.INDOORS))
				return false;
			if (!construction.ConstructionInsiderBoxCheck(player, part))
				return false;
			
			return true;
		}
		return false;
	}
	
	//! Does not work on server, since variants are not updated there (invoker does not invoke)
	protected ConstructionPart GetTargetPart(ConstructionActionData cad)
	{
		return cad.GetBuildPartInstantAtIndex(m_VariantID);
	}
};
#endif