% ------------------------- Domain Definition -------------------------
% --- Cross-file definitions ------------------------------------------
:- multifile connected/3, crate/3, agent/2.

% --- Primitive control actions ---------------------------------------
primitive_action(move(_, _)).
primitive_action(push(_, _)).

% --- Precondition for primitive actions ------------------------------
poss(move(From, To), S) :-
	agent(From, S),
	connected(From, To, _),
	not(crate(_, To, S)),
	not(visited(To, S)).

poss(push(From, Direction), S) :-
	agent(From, S),
	connected(From, CrateLocation, Direction),
   	crate(_, CrateLocation, S),
	connected(CrateLocation, CrateTarget, Direction),
   	not(crate(_, CrateTarget, S)).

% --- Successor state axioms ------------------------------------------
visited(Plek, result(A, _)) :-
	A = move(Plek, _).

agent(AgentPlek, result(A, S)) :-
	A = move(_, AgentPlek);
	A = push(OudeAgentPlek, Richting),
		connected(OudeAgentPlek, AgentPlek, Richting);
	not(A = move(AgentPlek, _)), not(A = push(AgentPlek, _)),
		agent(AgentPlek, S).
	
crate(Krat, Kratplek, result(A, S)) :-
	A = push(AgentPlek, Richting), 
		connected(AgentPlek, OudeKratPlek, Richting),
		connected(OudeKratPlek, Kratplek, Richting),
   		crate(Krat, OudeKratPlek, S);
	not(A = push(AgentPlek2, Richting2)),
		connected(AgentPlek2, Kratplek, Richting2),
		crate(Krat, Kratplek, S).
