First, thanks for testing the script! The second case can be solved, the first one might remain as a situation that a character can't handle properly (i. e. he'd need some turns) or at all (mostly when other characters block the path; but, at least, those characters closest to the blocking items would be able to solve the situation immediately or after a few attempts; some unnecessary behaviour might be solved by a new event we add, s. below).

2) Second first: it happens due to item weight:

Chests have 50,000 weight, so I have to increase the limit. This would also include Straw, Anvil B and Grain Sack, but unfortunately also a few unmovable objects. For special barrels (ooze, oil, water) we'd need 60,000 which isn't a problem since there don't seem to be other objects between 50,000 and 60,000 and no other items with 60,000. Do you think it would be okay to increase the weight of some unmovable 50,000 items to 61,000 to exclude them?* This would be:

GEN_HeavyMetal (probably; do you know what items this is for?)
Gen_Door_Weak (though doesn't seem to be used often, only found one in Cyseal, a tutorial door)
Gen_Stone_Indestructible
Gen_HeavyMetalLightSource (maybe, don't know which items have this stat)
Gen_SpawnHole_Weak (though probably irrelevant)
Gen_SpawnHole_Strong (same)
_TrapObjects

To leave them included wouldn't be too much of a problem but require more attempts to solve the situation.

*or decrease the weight of relevant 50,000 and 60,000 weight items to 40,000.

1) Yeah, big characters are quite limited in some situations. They often don't have an alternative path and often can't reach the temporary target either (due to blocking characters and other objects), so they move the wrong items, which are closer to them. Though smaller characters should be able to solve the situation after a while.
With 'instead of taking actions' you mean there would have been a possible target to attack but they had chosen another, unreachable one? It's hard to judge without knowing the exact circumstances, but they must have chosen an unreachable target by default (not my script) or the GetClose and MoveItems reactions where still active from their previous turns, so they didn't return to their default behaviour as long as they didn't reach the temporary target and the target where their movement initially failed. For this case - and other unintended behaviour related to unnecessarily active GetClose/MoveItems reactions - there should this event be added to the 'ABRAX_PathBlockAI' script, to make sure that they always try to execute default behaviour first on their turn and never execute actions that aren't necessary any more:

Code
EVENT SetPathAIPriorities
ON
	OnTurnEnded() //also thrown when __Me kills the last enemy to end combat
ACTIONS
	SetPriority("GetClose",0)
	SetPriority("MoveItems",0)


Whole script:

Code
INIT

CHARACTER:__Me

EXTERN FLOAT3:%TargetPos = null
FLOAT3:%TempTarget
INT:%ItemMoveSuccess = 0

/* //to be added to every reaction with movement

VARS
	FLOAT3:_Pos
INTERRUPT
Reset()
ON
		OnMovementFailed(_Pos)
	ACTIONS
	SetVar(__Me,"TargetPos",_Pos)
	CharacterEvent(__Me,"ActivateGetClose")
*/

BEHAVIOUR

REACTION GetClose, 0
USAGE PEACE	
USAGE COMBAT
VARS
	FLOAT:_distance
	FLOAT:_MyX
	FLOAT:_MyZ
	FLOAT:_TargetX
	FLOAT:_TargetZ
	FLOAT:_AttemptCounter = 0
	FLOAT:_AddX
	FLOAT:_AddZ
	FLOAT:_Divisor
	FLOAT3:_Target
	FLOAT3:_MyPos
	FLOAT3:_TargetPosition
ACTIONS
	IF "c1&c2"
		GetPosition(__Me,_MyPos)
		GetVar(_TargetPosition,__Me,"TargetPos")
	THEN
		Set(%TempTarget,_TargetPosition)
	ENDIF
	IF "c1&c2&c3&c4&c5"
		GetX(_MyPos,_MyX)
		GetZ(_MyPos,_MyZ)
		GetX(_TargetPosition,_TargetX)
		GetZ(_TargetPosition,_TargetZ)
		GetDistance(_distance,__Me,_TargetPosition)
	THEN
		Subtract(_TargetX,_MyX)
		Subtract(_TargetZ,_MyZ)
		GetRandom(_Divisor,1.8,1.9,2,2.1,2.2)
		Divide(_TargetX,_Divisor)
		Divide(_TargetZ,_Divisor)
		Add(_MyX,_TargetX)
		Add(_MyZ,_TargetZ)
		SetX(%TempTarget,_MyX)
		SetZ(%TempTarget,_MyZ)
		CharacterLookAt(%TempTarget)
		IF "c1"
			IsGreaterThen(_AttemptCounter,4)
		THEN
			Set(_AttemptCounter,0)
			SetPriority("MoveItems",0)
			IF "c1"
				IsInCombat(__Me)
			THEN
				CharacterEndTurn()
			ELSE
				DelayReaction("GetClose",5)
			ENDIF			
			SetPriority("GetClose",0)
		ELIF "c1"
			IsLessThen(_distance,4)
		THEN	
			CharacterLookAt(_TargetPosition)
			IF "c1"
				IsInCombat(__Me)
			THEN
				CharacterMoveTo(_TargetPosition,1,0,0,0.2,1)
			ELSE
				CharacterMoveTo(_TargetPosition,0,0,0,0.2,1)
			ENDIF
			SetPriority("GetClose",0)
		ELIF "!c1"
			IsLessThen(_distance,4)
		THEN			
			IF "!c1"
				FindValidPosition(%TempTarget,4,__Me)
			THEN
				Interrupt("GetClose")
			ENDIF
			IF "c1"
				IsInCombat(__Me)
			THEN
				CharacterMoveTo(%TempTarget,1,0,0,0.2,1.4)
			ELSE 
				CharacterMoveTo(%TempTarget,0,0,0,0.2,1.4) 
			ENDIF
			SetPriority("MoveItems",0)
		ELSE
			Set(_AttemptCounter,0)
			SetPriority("MoveItems",0)
			SetPriority("GetClose",0)
		ENDIF
	ENDIF
INTERRUPT
	Reset()
	ON
		OnMovementFailed(_)
		OnManualInterrupt("GetClose")
	ACTIONS
		Add(_AttemptCounter,1)
		SetPriority("MoveItems",3000)
		SetPriority("GetClose",0) 
		
REACTION MoveItems, 0
USAGE PEACE
USAGE COMBAT
VARS
	ITEM:_Item
	ITEM:_Item2
	ITEM:_IgnoreItem1
	ITEM:_IgnoreItem2
	ITEM:_IgnoreItem3
	FLOAT:_Weight
	FLOAT:_X
	FLOAT:_Z
	FLOAT:_MyPosX
	FLOAT:_MyPosZ
	FLOAT3:_MyPos
	CHARACTER:_Enemy
CHECK "(((((c1&c2)|(c3&c4))&c5&c6&((!c7&c8)|c9))|(c10&c11&c12&((!c13&c14)|c15)))&!c16)|(c17&c18)"
	IsRandom(0.4)
	ItemGet(_Item,__Me,6,Lowest,Distance,"")
	ItemGet(_Item,__Me,6,Random,Distance,"")
	CanSee(__Me,_Item)
	IsFacing(__Me,_Item)
	ItemGetStat(_Weight,_Item,Weight)
	IsLessThen(_Weight,1000)
	IsLessThen(_Weight,60001)
	IsEqual(_Weight,200000) //Ice_Crystal
	ItemGet(_Item,%TempTarget,6,Random,Distance,"")
	IsFacing(__Me,_Item)
	ItemGetStat(_Weight,_Item,Weight)
	IsLessThen(_Weight,1000)
	IsLessThen(_Weight,60001)
	IsEqual(_Weight,200000) //Ice_Crystal
	ItemIsDestroyed(_Item)
	IsInCombat(__Me)
	CharacterGet(_Enemy,__Me,5,Lowest,Distance,Enemy)
ACTIONS
	IF "!c1"
		IsEqual(_Enemy,null)
	THEN
		CharacterMoveTo(_Enemy,1)
		CharacterAttack(_Enemy)
		Goto("End")
	ENDIF
	IF "c1"
		IsInCombat(__Me)
	THEN
		CharacterMoveTo(_Item,1)
	ELSE
		CharacterMoveTo(_Item)
	ENDIF
	IF "c1"
		IsEqual(_Weight,200000) //Ice_Crystal
	THEN
		WHILE "!c1"
			ItemIsDestroyed(_Item)
		DO
			CharacterAttack(_Item)
		ENDWHILE
	ELSE
		GetPosition(__Me,_MyPos)
		GetRandom(_X,-3,-2,2,3)
		GetRandom(_Z,-3,-2,2,3)
		IF "!c1&c2&c3"
			ItemIsDestroyed(_Item)
			GetX(_MyPos,_MyPosX)
			GetZ(_MyPos,_MyPosZ)
		THEN
			Subtract(_MyPosX,_X)
			Subtract(_MyPosZ,_Z)
			SetX(_MyPos,_MyPosX)
			SetZ(_MyPos,_MyPosZ)
			IF "c1"
				FindValidPosition(_MyPos,6,_Item)
			THEN
				StartTimer("CheckMoveItemSuccess",3,0)
				CharacterMoveItem(_Item,_MyPos)
				Set(%ItemMoveSuccess,1)	
			ENDIF
		ENDIF
	ENDIF
	Label("End")
	Set(_Enemy,null)
	SetPriority("MoveItems",0)
INTERRUPT
	Reset()
	Set(_Enemy,null)
	SetPriority("MoveItems",0)
	
EVENTS

EVENT CheckItemMoveSuccess
ON
	OnTimer("CheckMoveItemSuccess")
ACTIONS
	IF "c1"
		IsEqual(%ItemMoveSuccess,1)
	THEN
		Set(%ItemMoveSuccess,0)
	ELSE
		Interrupt("MoveItems")
	ENDIF
	
EVENT GetCloseActivation
ON
	OnCharacterEvent(__Me,"ActivateGetClose")
ACTIONS
	SetPriority("GetClose",2000)
	
EVENT SetPathAIPriorities
ON
	OnTurnEnded() //also thrown when __Me kills the last enemy to end combat
ACTIONS
	SetPriority("GetClose",0)
	SetPriority("MoveItems",0)



Edit: Also looking through the object stats to improve the item selection. Seems a lot of small items (paintings, weapons etc.) can be excluded without much effort.

Last edited by Abraxas*; 24/02/17 10:43 PM.

My mods for DOS 1 EE: FasterAnimations - QuietDay - Samaritan