

future_past_person_visible(A, B, C, D) :-
	camera(C, E, F, G, H, I, J),
	rule_configuration(s_person_visible_window, K, L),
	step(M),
	head_positions(A, M, L, I, B, N),
	head_positions(A, -M, K, I, B, O),
	append(O, N, P),
	findall(Q, member((Q, R), P), S),
	findall(T, member((U, T), P), V),
	averlist(S, W),
	averlist(V, X),
	W>=E,
	X>=F,
	W<E+G,
	X<F+H,
	(   is_moving_virtual_camera(C)
	->  moving_virtual_camera_id(B, J)
	;   true
	),
	Y is 1-abs(E+G/2-W)/ (G/2),
	(   I=3
	->  Z is 1-min((X*0.5-F)/H, 1)
	;   Z is 1-min((X*1-F)/H, 1)
	),
	A1 is (Y+Z)/2,
	D is min(A1, 1).


write_done :-
	write(' done.'),
	nl,
	flush_output.


evaluation_estf(A) :-
	string_concat(A, '.est.txt', B),
	tell(B),
	evaluation_est,
	told.


export_virtual_camera_rectangles_step(A, B, C) :-
	(   A=<B
	->  set_virtual_camera_time(A),
	    ignore(export_virtual_camera_rectangles(A)),
	    D is A+C,
	    export_virtual_camera_rectangles_step(D, B, C)
	).


init :-
	init_import,
	import,
	init_head,
	init_hand,
	init_persons,
	init_virtual_cameras,
	init_person_activity,
	init_main.


evaluation_hand_moving(A, B, C, D) :-
	E is 5000,
	F is 5000,
	camera(C, G, H, I, J, K, L),
	step(M),
	hand_moves(A, M, F, K, B, N),
	hand_moves(A, -M, E, K, B, O),
	sumlist(N, P),
	sumlist(O, Q),
	D is (P+Q)/ (F+E).


get_hand_move(A, B, C, D, E) :-
	hand(A, C, F, D, G, H),
	I is A+B,
	hand(I, C, F, D, J, K),
	E is sqrt((J-G)**2+ (K-H)**2).


update_model_state(A) :-
	model_state(B),
	(   model_rule(C, A, B, D)
	*-> set_model_state(D)
	;   true
	).


is_virtual_camera(A) :-
	is_virtual_camera(A, B).


evaluation_techf(A) :-
	string_concat(A, '.tech.txt', B),
	tell(B),
	evaluation_tech,
	told.


head_full_positions(A, B, C, D, E, F) :-
	(   C=<0
	->  F=[]
	;   step(G),
	    H is A+G*B,
	    I is C-abs(G),
	    head_full_positions(H, B, I, D, E, J),
	    (   head(A, D, K, L, M, N, O, P, Q, E)
	    ->  F=[ (L, M, N, O, P, Q)|J]
	    ;   F=J
	    )
	).


camera(A, B, C, D, E, F, G) :-
	(   camera(A, D, E),
	    B is 0,
	    C is 0,
	    F=A,
	    G is 1
	;   virtual_camera(F, G, H, I, J),
	    camera(F, K, L),
	    A is F*10000+G,
	    B is I-K/2/H,
	    D is K/H,
	    C is J-L/2/H,
	    E is L/H
	;   A is-1,
	    B is-1,
	    C is-1,
	    D is-1,
	    E is-1,
	    F is-1,
	    G is-1
	).


on_camera(A, B, C) :-
	on_camera(A, B, C, D).


init_history :-
	retractall(output(A, B, C)),
	retractall(outputz(D, E, F)).


is_speaking(A, B) :-
	is_speaking(A, B, C).


find_max_cameras([], []).
find_max_cameras([A|B], C) :-
	find_max_cameras(B, D),
	(   D==[]
	->  C=[A]
	;   (E, F)=A,
	    nth0(0, D, G),
	    (H, I)=G,
	    (   I<F
	    ->  C=[A]
	    ;   I>F
	    ->  C=D
	    ;   append(D, [A], C)
	    )
	).


export_virtual_camera_rectangles(A) :-
	forall((camera(B, C, D, E, F, G, H), G\==B, B==20202), (I is C+E, J is D+F, export(virtual_camera, A, [ (camera, G), (object, B), (minx, C), (miny, D), (maxx, I), (maxy, J)]))).


init_head :-
	retractall(head_move(A, B, C, D)),
	(   rule_configuration(s_mode, offline)
	->  write_begin('generating head_move'),
	    begin(E),
	    end(F),
	    step(G),
	    ignore(generate_all_head_move_step(E, F, G)),
	    write_done
	;   true
	).


update_last_output_optimized(A) :-
	retractall(last_output_actual(B, C, D)),
	ignore((
	    last_output(A, E, F),
	    assert(last_output_actual(A, E, F))
	    )).


speaking_exp_base(A) :-
	A is-log(0.01).


head(A, B, C, D, E) :-
	head(A, B, F, D, E, G, H, I, J, C).


head_positions(A, B, C, D, E, F) :-
	(   C=<0
	->  F=[]
	;   G is A+B,
	    H is C-abs(B),
	    head_positions(G, B, H, D, E, I),
	    (   head(A, D, E, J, K)
	    ->  F=[ (J, K)|I]
	    ;   F=I
	    )
	).


evaluate_camera(A, B, C) :-
	bagof(D, E^add_camera_rule(E, A, B, D), F),
	sumlist(F, G),
	(   bagof(D, E^mult_camera_rule(E, A, B, D), H)
	->  multlist(H, I),
	    C is G*I
	;   C is G
	).


future_person_visible(A, B, C, D) :-
	fail,
	camera(C, E, F, G, H, I, J),
	(   I<0
	->  K is C
	;   K is I
	),
	future_person_visible_window(L),
	head_positions(A, 1, L, K, B, M),
	findall(N, member((N, O), M), P),
	findall(Q, member((R, Q), M), S),
	list_aver(P, T),
	list_aver(S, U),
	T>=E,
	U>=F,
	T<E+G,
	U<F+H,
	V is 1-abs(E+G/2-T)/ (G/2),
	W is 1- (U-F)/H,
	D is (V+W)/2.


rule_configuration(unused_rule_name).
rule_configuration(o_pip_in_third_camera).
rule_configuration(c_intro_virtual_supress).
rule_configuration(c_intro_physical).
rule_configuration(c_finish_virtual_supress).
rule_configuration(c_initial_random_camera).
rule_configuration(c_person_activity).
rule_configuration(c_virtual_supress_first).
rule_configuration(c_virtual_parent_anti_lazy).
rule_configuration(c_virtual_supress_same_parent).
rule_configuration(c_virtual_supress_other_parent).
rule_configuration(m_undefined_intro).
rule_configuration(m_intro_presentation).


sooner_same_camera(A, [B|C], D, E) :-
	(F, G)=B,
	(   G=A
	->  sooner_same_camera(A, C, H, I)
	->  D=H,
	    E is I+1
	;   D=F,
	    E is 0
	).


runf :-
	runf('output.pl').


do_step(A, B, C) :-
	(   A=<B
	->  ignore((
		real_time_generate(A),
		find_best_camera(A, D),
		insert_output(A, D)
		)),
	    E is A+C,
	    do_step(E, B, C)
	).


generate_moving_virtual_cameras :-
	write_begin('generating moving virtual cameras'),
	begin(A),
	end(B),
	step(C),
	retractall(moving_virtual_camera(D, E, F, G, H, I)),
	ignore(generate_moving_virtual_cameras_step(A, B, C)),
	write_done.


init_main :-
	init_history,
	retractall(temp_configuration(A, B)),
	set_model_state(undefined).


on_camera(A, B, C, D) :-
	on_camera0(A, B, C, D),
	not(sooner_on_camera0(A, B, C, D)).


rule_configuration(unused_rule_name, value1, value2, value3, value4, value5, value6).


is_speaking_all(A, B, C) :-
	start_speaking(D, B),
	D=<A,
	not(stop_speaking(D, B)),
	not((
	    stop_speaking(E, B),
	    E>=D,
	    E=<A,
	    not(start_speaking(E, B))
	    )),
	C is A-D.


evaluation_moving(A, B, C) :-
	bagof(C, D^ (camera(D), not(is_virtual_camera(D)), not(is_empty_camera(D)), evaluation_head_moving(A, B, D, E), evaluation_hand_moving(A, B, D, F), C is max(E, F)), G),
	maxlist(G, C),
	C>0.


hand(A, B, C, D) :-
	hand(A, B, C, E, F, G, H, I, J, D).


averlist(A, B) :-
	sumlist(A, C),
	length(A, D),
	D>0,
	B is C/D.


generate_person_activity(A) :-
	ignore(forall(person(B), (evaluate_person_activity(A, B, C), assert(person_activity(A, B, C))))).


start_speaking1(A, B) :-
	person_interactivity(A, B, C),
	get_parameter(C, interactivity, D),
	(   D=talking
	;   D=laughing
	).


hand0(A, B, C, D, E, F, G, H, I, J) :-
	event_hand(A, K),
	get_parameter(K, camera, B),
	get_parameter(K, object, C),
	get_parameter(K, centerx, D),
	get_parameter(K, centery, E),
	get_parameter(K, minx, F),
	get_parameter(K, miny, G),
	get_parameter(K, maxx, H),
	get_parameter(K, maxy, I),
	get_parameter(K, person, J).


is_moving_virtual_camera(A) :-
	camera(A, B, C, D, E, F, G),
	F\==A,
	is_moving_virtual_camera_id(G).


add_camera_rule(A, B, C, D) :-
	A=c_anti_swap,
	rule_configuration(A, E),
	last_output_optimized(B, F, G),
	F=C,
	G<E,
	D is 1.
add_camera_rule(A, B, C, D) :-
	A=c_const,
	rule_configuration(A, C, D).
add_camera_rule(A, B, C, D) :-
	A=c_initial_random_camera,
	rule_configuration(A),
	not(is_empty_camera(C)),
	not(output(E, F, G)),
	D is 1.
add_camera_rule(A, B, C, D) :-
	A=c_random_camera,
	rule_configuration(A),
	not(is_empty_camera(C)),
	D is 1.
add_camera_rule(A, B, C, D) :-
	A=c_person_activity,
	rule_configuration(A),
	not(is_empty_camera(C)),
	findall(E, (person_activity(B, F, G), (G>0->future_past_person_visible(B, F, C, H);H is 0), E is G*H), I),
	(   I=[]
	->  fail
	;   sumlist(I, J)
	),
	person_count(K),
	D is J/K.
add_camera_rule(A, B, C, D) :-
	A=c_intro_physical,
	rule_configuration(A),
	model_state(intro),
	not(is_empty_camera(C)),
	(   setof(E, F^G^ (output(F, E, G), F<B), H)
	->  true
	;   H=[]
	),
	not(member(C, H)),
	(   add_camera_rule(c_person_activity, B, C, I)
	->  true
	;   I is 0
	),
	D is 2* (1-I).
add_camera_rule(A, B, C, D) :-
	A=c_summarization1,
	C= -1,
	rule_configuration(A, E),
	(   temp_configuration(A, F)
	->  G=F
	;   G=E
	),
	findall(H, person_activity(B, I, H), J),
	sumlist(J, K),
	person_count(L),
	M is K/L,
	D is (1-M)*G.
add_camera_rule(A, B, C, D) :-
	A=c_summarization2,
	C= -1,
	rule_configuration(A, E),
	(   temp_configuration(A, F)
	->  G=F
	;   G=E
	),
	findall(H, person_activity(B, I, H), J),
	sumlist(J, K),
	person_count(L),
	M is K/L,
	M<G,
	D is 1.
add_camera_rule(A, B, C, D) :-
	A=c_summarization3,
	C= -1,
	rule_configuration(A, E),
	(   temp_configuration(A, F)
	->  G=F
	;   G=E
	),
	findall(H, person_activity(B, I, H), J),
	sumlist(J, K),
	person_count(L),
	M is K/L,
	step(N),
	O is B-N,
	findall(P, person_activity(O, Q, P), R),
	sumlist(R, S),
	T is S/L,
	D is (1-abs(M-T))*G.


real_time_generate(A) :-
	step(B),
	ignore((
	    (   rule_configuration(s_mode, realtime)
	    ->  generate_all_head_move(A, B),
		generate_all_hand_move(A, B)
	    )
	    )).


head(A, B, C) :-
	head(A, B, D, E, F, G, H, I, J, C).


head_moves(A, B, C, D, E, F) :-
	(   C=<0
	->  F=[]
	;   G is A+B,
	    H is C-abs(B),
	    head_moves(G, B, H, D, E, I),
	    (   head_move(A, D, E, J)
	    ->  F=[J|I]
	    ;   F=I
	    )
	).


run_main :-
	begin(A),
	end(B),
	step(C),
	ignore(do_step(A, B, C)).


sooner_on_camera0(A, B, C, D) :-
	on_camera0(A, B, C, E),
	E>D.


evaluation_est :-
	clear_eval_value(shot_count),
	clear_eval_value(shot_short),
	clear_eval_value(shot_long),
	clear_eval_value(shot_vsp),
	clear_eval_value(shot_vpr),
	clear_eval_value(shot_move),
	begin(A),
	end(B),
	step(C),
	ignore(evaluation_est_step(A, B, C)),
	print_eval_value(shot_count),
	print_eval_value(shot_short),
	print_eval_value(shot_long),
	print_eval_value(shot_vsp),
	print_eval_value(shot_vpr),
	print_eval_value(shot_move),
	print_eval_perc2([shot_short, shot_long, shot_vsp, shot_vpr, shot_move], shot_count).


virtual_camera_position(A, B) :-
	B is 1- (cos(A*pi)+1)/2.


is_speaking(A, B, C) :-
	bagof(C, is_speaking_all(A, B, C), D),
	maxlist(D, C).


rule_configuration(unused_rule_name, value1).
rule_configuration(s_mode, realtime).
rule_configuration(o_summarization_fade, 240).
rule_configuration(c_anti_swap, 240).
rule_configuration(c_virtual_supress_parent, 3).
rule_configuration(p_past_speaking_exp, 10000).
rule_configuration(m_presentation_finish, 5000).


hand(A, B, C, D, E, F) :-
	hand(A, B, C, E, F, G, H, I, J, D).


test_person_activity_step(A, B, C, D, E) :-
	(   B=<C
	->  (   evaluate_person_activity(B, A, F)
	    ->  export(graph, B, [ (color, E), (value, F)])
	    ;   true
	    ),
	    G is B+D,
	    test_person_activity_step(A, G, C, D, E)
	).


test_person_rule(A, B) :-
	test_person_rule(A, B, 0).


head0(A, B, C, D, E, F, G, H, I, J) :-
	event_head(A, K),
	get_parameter(K, camera, B),
	get_parameter(K, object, C),
	get_parameter(K, centerx, D),
	get_parameter(K, centery, E),
	get_parameter(K, minx, F),
	get_parameter(K, miny, G),
	get_parameter(K, maxx, H),
	get_parameter(K, maxy, I),
	get_parameter(K, person, J).


person_rule(A, B, C, D) :-
	bagof(E, F^G^ (camera(F, H, I, J, K, G, L), F=G, person_rule(A, B, C, F, E)), M),
	maxlist(M, D).
person_rule(A, B, C, D) :-
	A=p_const,
	rule_configuration(A, C, D).
person_rule(A, B, C, D) :-
	A=p_past_speaking_exp,
	rule_configuration(A, E),
	is_speaking(B, C, F),
	speaking_exp_base(G),
	D is 1-exp(-G* (F/E)).
person_rule(A, B, C, D) :-
	A=p_past_speaking_inv_exp,
	rule_configuration(A, E),
	is_speaking(B, C, F),
	speaking_exp_base(G),
	D is exp(-G* (F/E)).
person_rule(A, B, C, D) :-
	A=p_past_speaking_cos,
	rule_configuration(A, E),
	is_speaking(B, C, F),
	D is 1- (cos(min(F, E)/E*pi)+1)/2.
person_rule(A, B, C, D) :-
	A=p_future_speaking_exp,
	rule_configuration(A, E),
	will_speak(B, C, F),
	speaking_exp_base(G),
	F<E,
	D is 1-exp(-G* ((E-F)/E)).
person_rule(A, B, C, D) :-
	A=p_future_speaking_cos,
	rule_configuration(A, E),
	will_speak(B, C, F),
	F<E,
	D is 1- (cos((E-F)/E*pi)+1)/2.
person_rule(A, B, C, D) :-
	A=p_future_past_speaking_exp,
	rule_configuration(A, E, F),
	(   will_speak(B, C, G)
	->  G<E,
	    H is E-G
	;   is_speaking(B, C, I)
	->  H is E+I
	;   fail
	),
	speaking_exp_base(J),
	D is 1-exp(-J* (H/ (E+F))).


is_empty_camera(A) :-
	A<0.


mult_camera_rule(A, B, C, D) :-
	A=c_anti_quick,
	last_output_optimized(B, E, F),
	C\==E,
	rule_configuration(A, G, H),
	(   F<G
	->  D is 0
	;   camera_exp_base(I),
	    D is 1- (cos((1-exp(-I* ((F-G)/ (H-G))))*pi)+1)/2
	).
mult_camera_rule(A, B, C, D) :-
	A=c_anti_lazy,
	last_output_optimized(B, E, F),
	C==E,
	rule_configuration(A, G, H),
	(   F<G
	->  D is 1
	;   camera_exp_base(I),
	    D is 1- (cos(exp(-I* ((F-G)/ (H-G)))*pi)+1)/2
	).
mult_camera_rule(A, B, C, D) :-
	A=c_virtual_supress_first,
	rule_configuration(A),
	camera(C, E, F, G, H, I, J),
	I\==C,
	not(output(K, L, M)),
	D is 0.
mult_camera_rule(A, B, C, D) :-
	A=c_virtual_parent_anti_lazy,
	rule_configuration(A),
	last_output_optimized(B, E),
	camera(E, F, G, H, I, J, K),
	E\==J,
	C==J,
	mult_camera_rule(c_anti_lazy, B, E, D).
mult_camera_rule(A, B, C, D) :-
	A=c_virtual_supress_same_parent,
	rule_configuration(A),
	camera(C, E, F, G, H, I, J),
	I\==C,
	last_output_optimized(B, K),
	C\==K,
	camera(K, L, M, N, O, P, Q),
	K\==P,
	I==P,
	D is 0.
mult_camera_rule(A, B, C, D) :-
	A=c_virtual_supress_other_parent,
	rule_configuration(A),
	camera(C, E, F, G, H, I, J),
	I\==C,
	last_output_optimized(B, K),
	I\==K,
	C\==K,
	(   pred_last_output(B, K, L, M)
	->  L\==C
	;   true
	),
	D is 0.
mult_camera_rule(A, B, C, D) :-
	A=c_virtual_supress_parent,
	rule_configuration(A, E),
	camera(C, F, G, H, I, E, J),
	E\==C,
	D is 0.
mult_camera_rule(A, B, C, D) :-
	A=c_intro_virtual_supress,
	rule_configuration(A),
	model_state(intro),
	is_virtual_camera(C),
	D is 0.
mult_camera_rule(A, B, C, D) :-
	A=c_finish_virtual_supress,
	rule_configuration(A),
	model_state(finish),
	is_virtual_camera(C),
	D is 0.
mult_camera_rule(A, B, C, D) :-
	A=c_intro_physical,
	rule_configuration(A),
	model_state(intro),
	not(is_empty_camera(C)),
	(   setof(E, F^G^ (output(F, E, G), F<B), H)
	->  true
	;   H=[]
	),
	member(C, H),
	D is 0.
mult_camera_rule(A, B, C, D) :-
	A=c_summarization_supress,
	rule_configuration(A),
	C= -1,
	not(output(E, F, G)),
	D is 0.


person_interactivity(A, B, C) :-
	(   event_person1_interactivity(A, C),
	    B=a
	;   event_person2_interactivity(A, C),
	    B=b
	;   event_person3_interactivity(A, C),
	    B=c
	;   event_person4_interactivity(A, C),
	    B=d
	).


rule_configuration(unused_rule_name, value1, value2, value3, value4).


generate_all_head_move_step(A, B, C) :-
	(   A=<B
	->  ignore(generate_all_head_move(A, C)),
	    D is A+C,
	    generate_all_head_move_step(D, B, C)
	).


run :-
	init_main,
	run_main.


last_output_parameters(A, B, C) :-
	once((
	    output(D, B, C),
	    D=<A
	    )).


model_rule(A, B, undefined, intro) :-
	A=m_undefined_intro,
	rule_configuration(A).
model_rule(A, B, intro, presentation) :-
	A=m_intro_presentation,
	rule_configuration(A),
	(   setof(C, D^E^ (output(D, C, E), D<B), F)
	->  true
	;   F=[]
	),
	(   setof(C, (camera(C), not(is_empty_camera(C)), not(is_virtual_camera(C))), G)
	->  true
	;   G=[]
	),
	subset(G, F).
model_rule(A, B, presentation, finish) :-
	A=m_presentation_finish,
	rule_configuration(A, C),
	end(D),
	D-B<C.


set_model_state(A) :-
	retractall(model_state(B)),
	assert(model_state(A)).


past_person_visible(A, B, C, D) :-
	fail,
	camera(C, E, F, G, H, I, J),
	(   I<0
	->  K is C
	;   K is I
	),
	past_person_visible_window(L),
	head_positions(A, 1, L, K, B, M),
	findall(N, member((N, O), M), P),
	findall(Q, member((R, Q), M), S),
	list_aver(P, T),
	list_aver(S, U),
	T>=E,
	U>=F,
	T<E+G,
	U<F+H,
	V is 1-abs(E+G/2-T)/ (G/2),
	W is 1- (U-F)/H,
	D is (V+W)/2.


last_output_parameters(A, B, C, D) :-
	once((
	    output(E, B, D),
	    E=<A
	    )),
	(   once((
		output(F, G, H),
		F=<E,
		G\=B
		))
	->  true
	;   F is-1000000
	),
	findall(I, I^J^ (output(I, B, J), I>F, I=<E), K),
	last(K, L),
	C is A-L.


init_virtual_cameras :-
	retractall(virtual_camera(A, B, C, D, E)),
	assert(moving_virtual_camera(0, 0, 0, 0, 0, 0)),
	retractall(moving_virtual_camera(F, G, H, I, J, K)),
	ignore((
	    (   rule_configuration(s_fixed_virtual_cameras, L, M, N, O, P)
	    *-> generate_fixed_virtual_cameras
	    )
	    )),
	ignore((
	    (   rule_configuration(s_moving_virtual_cameras, Q, R, S, T, U, V)
	    ->  generate_moving_virtual_cameras
	    )
	    )),
	set_virtual_camera_time(0).


is_speakingX(A, B, C) :-
	once(is_speaking_all(A, B, C)).


test_person_activity(A, B) :-
	begin(C),
	end(D),
	step(E),
	(   test_person_activity_step(A, C, D, E, B)
	;   true
	).


maxlist([A], B) :-
	B is A.
maxlist([A|B], C) :-
	maxlist(B, D),
	(   D>A
	->  C is D
	;   C is A
	).


test_person_rulef(A, B, C) :-
	string_concat(A, '_', D),
	string_concat(D, B, E),
	string_concat(E, '_', F),
	G=F,
	string_concat(G, '.pl', H),
	tell(H),
	test_person_rule(A, B, C),
	told.
test_person_rulef(A, B, C) :-
	test_person_rulef(A, B, C, 0).


head(A, B, C, D, E, F) :-
	head(A, B, C, E, F, G, H, I, J, D).


evaluate_cameras(A, [], []).
evaluate_cameras(A, [B|C], D) :-
	evaluate_cameras(A, C, E),
	(   evaluate_camera(A, B, F),
	    F>0
	->  append(E, [ (B, F)], D)
	;   D=E
	).


insert_output(A, B) :-
	findall(C, output_rule_order(C), D),
	evaluate_output_step(A, B, [], E, D),
	(   last_output_parameters(A, F, G)
	->  true
	;   F=[],
	    G=[]
	),
	(   (   B\=F
	    ;   E\=G
	    )
	->  asserta(output(A, B, E)),
	    export(output, A, E),
	    flush_output
	;   true
	).


rule_configuration(unused_rule_name, value1, value2, value3).
rule_configuration(o_virtual_cameras_zooming_moving, 1000, 1, 0).
rule_configuration(p_past_head_moving, 2000, 0.025, 0.25).
rule_configuration(p_past_hand_moving, 2000, 0.025, 0.25).


evaluate_person_activity(A, B, C) :-
	rule_configuration(s_person_mult, B, D),
	findall(E, person_rule(F, A, B, E), G),
	(   G=[]
	->  H is 0
	;   maxlist(G, H)
	),
	C is min(H*D, 1.0).


inc_eval_value(A) :-
	eval_value(A, B),
	retractall(eval_value(A, C)),
	D is B+1,
	assert(eval_value(A, D)).


stop_speaking0(A, B) :-
	event_stop_speaking(A, C),
	get_parameter(C, person, B).


export(A, B, C) :-
	write(event_),
	write(A),
	write('('),
	write(B),
	write(', ['),
	export_parameters(C),
	write(']).'),
	nl.


runf(A) :-
	tell(A),
	run,
	told.


last_output_parametersX(A, B, C) :-
	findall((D, E), (output(D, E, F), D=<A), G),
	sort(G, H),
	last(H, (I, B)),
	output(I, B, C).


do_realtime_step(A, B) :-
	once(find_best_camera(A, C)),
	findall(D, output_rule_order(D), E),
	evaluate_output_step(A, C, [], B, E),
	(   last_output_parameters(A, F, G)
	->  true
	;   F=[],
	    G=[]
	),
	(   (   C\=F
	    ;   B\=G
	    )
	->  asserta(output(A, C, B))
	;   fail
	).


import :-
	retractall(head(A, B, C, D, E, F, G, H, I, J)),
	retractall(hand(K, L, M, N, O, P, Q, R, S, T)),
	retractall(start_speaking(U, V)),
	retractall(stop_speaking(W, X)),
	write_begin(importing),
	import_step,
	write_done.


pred_last_outputX(A, B, C, D) :-
	findall((E, F), (output(E, F, G), E=<A), H),
	sort(H, I),
	reverse(I, J),
	nth0(0, J, (K, L)),
	(   L\=B
	->  C=L,
	    D is 0
	;   sooner_same_camera(L, J, M, N),
	    D is A-M,
	    O is N+1,
	    nth0(O, J, (P, C))
	).


generate_moving_virtual_cameras_step(A, B, C) :-
	(   A=<B
	->  init_moving_virtual_cameras(A),
	    D is A+C,
	    generate_moving_virtual_cameras_step(D, B, C)
	).


last_output(A, B) :-
	last_output_parameters(A, B, C).


output_rule_order(o_basic).
output_rule_order(o_summarization_fade).
output_rule_order(o_virtual_cameras_zooming_moving).
output_rule_order(o_virtual_cameras_simple).
output_rule_order(o_pip_in_third_camera).


get_parameter([ (A, B)|C], D, E) :-
	(   A=D
	->  E=B
	;   get_parameter(C, D, E)
	).


evaluate_est(A, B, C) :-
	step(D),
	E is A-D,
	last_output(E, F, G),
	(   G=<1000
	->  inc_eval_value(shot_short)
	).
evaluate_est(A, B, C) :-
	step(D),
	E is A-D,
	last_output(E, F, G),
	(   G>=30000
	->  inc_eval_value(shot_long)
	).
evaluate_est(A, B, C) :-
	is_virtual_camera(B, D),
	is_virtual_camera(C, E),
	(   D==E
	->  inc_eval_value(shot_vsp)
	).
evaluate_est(A, B, C) :-
	is_virtual_camera(C, D),
	D\==B,
	step(E),
	F is A-E,
	(   pred_last_output(F, B, G, H)
	->  G\==C
	;   true
	),
	inc_eval_value(shot_vpr).
evaluate_est(A, B, C) :-
	C==3,
	step(D),
	E is A-D,
	pred_last_output(E, B, F, G),
	F\==C,
	last_output(E, H, I),
	J is A-I,
	(   once((
		person(K),
		evaluation_person_visible(A, C, K),
		evaluation_person_visible(J, B, K)
		))
	->  fail
	;   true
	),
	inc_eval_value(shot_move).


rule_configuration(unused_rule_name, value1, value2, value3, value4, value5).
rule_configuration(s_fixed_virtual_cameras, 1, 101, 2, 180, 276).
rule_configuration(s_fixed_virtual_cameras, 1, 102, 2, 500, 276).
rule_configuration(s_fixed_virtual_cameras, 2, 101, 2, 180, 276).
rule_configuration(s_fixed_virtual_cameras, 2, 102, 2, 500, 276).


init_person_activity :-
	retractall(person_activity(A, B, C)),
	(   rule_configuration(s_mode, offline)
	->  write_begin('generating persons actvity'),
	    begin(D),
	    end(E),
	    step(F),
	    ignore(generate_person_activity_step(D, E, F)),
	    write_done
	;   true
	).


evaluation_max_moving(A, B) :-
	bagof((C, D), D^ (person(D), evaluation_moving(A, D, C)), E),
	sort(E, F),
	reverse(F, B).


test_person_activityf(A, B) :-
	C=activity,
	string_concat(C, '_', D),
	string_concat(D, A, E),
	string_concat(E, '.pl', F),
	tell(F),
	test_person_activity(A, B),
	told.


virtual_camera_percent(A, B, C, D, E) :-
	virtual_camera(A, B, C, F, G),
	camera(A, H, I, J, K),
	D is 100*F/J,
	E is 100*G/K.


write_begin(A) :-
	write(A),
	write(...),
	flush_output.


evaluation_person_visible(A, B, C) :-
	camera(B, D, E, F, G, H, I),
	J is 520,
	K is 520,
	step(L),
	head_positions(A, L, K, H, C, M),
	head_positions(A, -L, J, H, C, N),
	append(N, M, O),
	findall(P, member((P, Q), O), R),
	findall(S, member((T, S), O), U),
	averlist(R, V),
	averlist(U, W),
	V>=D,
	W>=E,
	V<D+F,
	W<E+G,
	(   is_moving_virtual_camera(B)
	->  moving_virtual_camera_id(C, I)
	;   true
	).


multlist([A], B) :-
	B is A.
multlist([A|B], C) :-
	multlist(B, D),
	C is A*D.


generate_all_hand_move_step(A, B, C) :-
	(   A=<B
	->  ignore(generate_all_hand_move(A, C)),
	    D is A+C,
	    generate_all_hand_move_step(D, B, C)
	).


hand_moves(A, B, C, D, E, F) :-
	(   C=<0
	->  F=[]
	;   G is A+B,
	    H is C-abs(B),
	    hand_moves(G, B, H, D, E, I),
	    (   hand_move(A, D, E, J)
	    ->  F=[J|I]
	    ;   F=I
	    )
	).


evaluation_tech :-
	clear_eval_value(speaking_hit),
	clear_eval_value(speaking_miss),
	clear_eval_value(speaking_hit2),
	clear_eval_value(speaking_miss2),
	clear_eval_value(moving_hit),
	clear_eval_value(moving_miss),
	clear_eval_value(moving_hit2),
	clear_eval_value(moving_miss2),
	clear_eval_value(moving_hit3),
	clear_eval_value(moving_miss3),
	clear_eval_value(moving_hit4),
	clear_eval_value(moving_miss4),
	begin(A),
	end(B),
	step(C),
	ignore(evaluation_tech_step(A, B, C)),
	print_eval_value(speaking_hit),
	print_eval_value(speaking_miss),
	print_eval_perc(speaking_hit, speaking_miss),
	print_eval_value(speaking_hit2),
	print_eval_value(speaking_miss2),
	print_eval_perc(speaking_hit2, speaking_miss2),
	print_eval_value(moving_hit),
	print_eval_value(moving_miss),
	print_eval_perc(moving_hit, moving_miss),
	print_eval_value(moving_hit2),
	print_eval_value(moving_miss2),
	print_eval_perc(moving_hit2, moving_miss2),
	print_eval_value(moving_hit3),
	print_eval_value(moving_miss3),
	print_eval_perc(moving_hit3, moving_miss3),
	print_eval_value(moving_hit4),
	print_eval_value(moving_miss4),
	print_eval_perc(moving_hit4, moving_miss4).


is_virtual_camera(A, B) :-
	camera(A, C, D, E, F, B, G),
	B\==A.


print_eval_value(A) :-
	eval_value(A, B),
	write(A),
	tab(1),
	write(B),
	nl.


start_speaking0(A, B) :-
	event_start_speaking(A, C),
	get_parameter(C, person, B).


generate_person_activity_step(A, B, C) :-
	(   A=<B
	->  generate_person_activity(A),
	    D is A+C,
	    generate_person_activity_step(D, B, C)
	).


summarization_step(A, B, C) :-
	(   A=<B
	->  string_concat(output, '_', D),
	    string_concat(D, A, E),
	    string_concat(E, '.pl', F),
	    tell(F),
	    init_main,
	    assert(temp_configuration(c_summarization1, A)),
	    assert(temp_configuration(c_summarization2, A)),
	    assert(temp_configuration(c_summarization3, A)),
	    run_main,
	    get_length(G),
	    export(result, 0, [ (treshold, A), (length, G)]),
	    told,
	    H is A+C,
	    summarization_step(H, B, C)
	;   true
	).


export_parameters([]).
export_parameters([ (A, B)|C]) :-
	write('('),
	write(A),
	write(', '),
	write(B),
	write(')'),
	(   C\==[]
	->  write(', ')
	;   true
	),
	export_parameters(C).


generate_all_hand_move(A, B) :-
	forall((bagof(C, get_hand_move(A, -B, D, E, C), F), averlist(F, G)), assert(hand_move(A, D, E, G))).


last_output_parametersXX(A, B, C, D) :-
	once((
	    output(E, B, D),
	    E=<A
	    )),
	(   once((
		output(F, G, H),
		F=<E,
		G\=B
		))
	->  true
	;   F is-1000000
	),
	once((
	    outputz(I, B, J),
	    I>F,
	    I=<E
	    )),
	C is A-I.


generate_all_persons :-
	write_begin('generating persons'),
	retractall(person(A)),
	(   setof(B, C^start_speaking(C, B), D)
	;   D=[]
	),
	(   setof(B, C^stop_speaking(C, B), E)
	;   E=[]
	),
	(   setof(B, C^F^G^hand(C, F, G, B), H)
	;   H=[]
	),
	(   setof(B, C^F^head(C, F, B), I)
	;   I=[]
	),
	union(D, E, J),
	union(H, I, K),
	union(J, K, L),
	forall(member(M, L), assert(person(M))),
	write_done.


output_rule(A, B, C, D, E) :-
	A=o_basic,
	E=[ (camera, C)].
output_rule(A, B, C, D, E) :-
	A=o_summarization_fade,
	rule_configuration(A, F),
	member((camera, G), D),
	pred_last_output(B, G, H, I),
	I<F,
	(   G= -1
	->  J is 100* (I/F),
	    K is J,
	    step(L),
	    M is min(100* ((I+L)/F), 100),
	    delete(D, (camera, G), N),
	    append(N, [ (camera, H), (effect1, fade), (fadepercent, J), (fadecolor, '0x00ffffff'), (audioeffect1, audiofade), (audiofadepercentbegin, K), (audiofadepercentend, M)], E)
	;   H= -1
	->  J is 100* ((F-I)/F),
	    K is J,
	    step(L),
	    M is max(100* ((F-I-L)/F), 0),
	    append(D, [ (effect1, fade), (fadepercent, J), (fadecolor, '0x00ffffff'), (audioeffect1, audiofade), (audiofadepercentbegin, K), (audiofadepercentend, M)], E)
	).
output_rule(A, B, C, D, E) :-
	A=o_pip_in_third_camera,
	rule_configuration(A),
	camera(C, F, G, H, I, J, K),
	J\==3,
	pred_last_output(B, C, L, M),
	L==3,
	N is 20,
	findall(O, P^Q^ (person(P), future_past_person_position(B, P, L, O, Q)), R),
	R\==[],
	camera(L, S, T),
	(   forall(member(O, R), O>=S/2)
	->  U is N,
	    V= (J==2)
	;   forall(member(O, R), O<S/2)
	->  U is 100-N,
	    V= (J==1)
	;   fail
	),
	(   V
	->  append(D, [ (effect3, hmirror)], W)
	;   W=D
	),
	append(W, [ (effect4, stack), (stackcamera, 1000000), (effect5, basic), (basiccamera, L), (effect6, pip), (pipcamera, 1000000), (pipcenterx, U), (pipcentery, '20'), (pipratio, '0.4')], E).
output_rule(A, B, C, D, E) :-
	A=o_virtual_cameras_zooming_moving,
	rule_configuration(A, F, G, H),
	member((camera, I), D),
	pred_last_output(B, I, J, K),
	camera(I, L, M, N, O, P, Q),
	(   K<F
	->  camera(J, R, S, T, U, V, W),
	    (   I\==P,
		J==V,
		P==V,
		G\==0
	    ->  virtual_camera_percent(P, Q, X, Y, Z),
		A1 is 50,
		B1 is 50,
		virtual_camera_position(K/F, C1),
		D1 is 1+C1* (X-1),
		E1 is C1*X/ (C1* (X-1)+1),
		F1 is (1-E1)*A1+E1*Y,
		G1 is (1-E1)*B1+E1*Z,
		delete(D, (camera, I), H1),
		append(H1, [ (camera, P), (effect2, zoom), (zoomratio, D1), (zoomcenterx, F1), (zoomcentery, G1)], E)
	    ;   I==P,
		J\==V,
		I==V,
		G\==0
	    ->  virtual_camera_percent(V, W, X, Y, Z),
		A1 is 50,
		B1 is 50,
		virtual_camera_position(1-K/F, C1),
		D1 is 1+C1* (X-1),
		E1 is C1*X/ (C1* (X-1)+1),
		F1 is (1-E1)*A1+E1*Y,
		G1 is (1-E1)*B1+E1*Z,
		append(D, [ (effect2, zoom), (zoomratio, D1), (zoomcenterx, F1), (zoomcentery, G1)], E)
	    ;   I\==P,
		J\==V,
		P==V,
		I\==J,
		H\==0
	    ->  virtual_camera_percent(P, Q, X, Y, Z),
		virtual_camera_percent(V, W, I1, J1, K1),
		virtual_camera_position(K/F, C1),
		D1 is (1-C1)*I1+C1*X,
		F1 is (1-C1)*J1+C1*Y,
		G1 is (1-C1)*K1+C1*Z,
		delete(D, (camera, I), H1),
		append(H1, [ (camera, P), (effect2, zoom), (zoomratio, D1), (zoomcenterx, F1), (zoomcentery, G1)], E)
	    ;   I\==P,
		virtual_camera_percent(P, Q, D1, F1, G1),
		delete(D, (camera, I), H1),
		append(H1, [ (camera, P), (effect2, zoom), (zoomratio, D1), (zoomcenterx, F1), (zoomcentery, G1)], E)
	    )
	;   I\==P,
	    virtual_camera_percent(P, Q, D1, F1, G1),
	    delete(D, (camera, I), H1),
	    append(H1, [ (camera, P), (effect2, zoom), (zoomratio, D1), (zoomcenterx, F1), (zoomcentery, G1)], E)
	).
output_rule(A, B, C, D, E) :-
	A=o_virtual_cameras_simple,
	rule_configuration(A),
	member((camera, F), D),
	camera(F, G, H, I, J, K, L),
	F\==K,
	virtual_camera_percent(K, L, M, N, O),
	delete(D, (camera, F), P),
	append(P, [ (camera, K), (effect2, zoom), (zoomratio, M), (zoomcenterx, N), (zoomcentery, O)], E).


init_hand :-
	retractall(hand_move(A, B, C, D)),
	(   rule_configuration(s_mode, offline)
	->  write_begin('generating head_move'),
	    begin(E),
	    end(F),
	    step(G),
	    ignore(generate_all_hand_move_step(E, F, G)),
	    write_done
	;   true
	).


will_speak(A, B, C) :-
	not(is_speaking(A, B)),
	start_speaking(D, B),
	D>A,
	not(stop_speaking(D, B)),
	not((
	    start_speaking(E, B),
	    E>A,
	    E<D,
	    not(stop_speaking(E, B))
	    )),
	not((
	    stop_speaking(F, B),
	    F>A,
	    F<D,
	    not(start_speaking(F, B))
	    )),
	C is D-A.


evaluation_est_step(A, B, C) :-
	(   A=<B
	->  ignore((
		D is A-C,
		last_output(A, E),
		last_output(D, F),
		E\==F,
		inc_eval_value(shot_count),
		once(evaluate_est(A, F, E))
		)),
	    G is A+C,
	    evaluation_est_step(G, B, C)
	).


init_import :-
	(   rule_configuration(s_mode, realtime)
	->  retractall(event_head(A, B)),
	    retractall(event_hand(C, D)),
	    retractall(event_start_speaking(E, F)),
	    retractall(event_stop_speaking(G, H))
	;   true
	).


camera(A) :-
	camera(A, B, C, D, E, F, G).


future_past_person_position(A, B, C, D, E) :-
	camera(C, F, G, H, I, J, K),
	C==J,
	rule_configuration(s_person_visible_window, L, M),
	step(N),
	head_positions(A, N, M, J, B, O),
	head_positions(A, -N, L, J, B, P),
	append(P, O, Q),
	findall(R, member((R, S), Q), T),
	findall(U, member((V, U), Q), W),
	averlist(T, D),
	averlist(W, E),
	D>=F,
	E>=G,
	D<F+H,
	E<G+I.


evaluate_tech(A) :-
	forall(is_speaking(A, B), (last_output(A, C), evaluation_person_visible(A, C, B)->inc_eval_value(speaking_hit);inc_eval_value(speaking_miss))).
evaluate_tech(A) :-
	bagof(B, is_speaking(A, B), C),
	(   once((
		member(D, C),
		last_output(A, E),
		evaluation_person_visible(A, E, D)
		))
	->  inc_eval_value(speaking_hit2)
	;   inc_eval_value(speaking_miss2)
	).
evaluate_tech(A) :-
	evaluation_max_moving(A, B),
	nth0(0, B, (C, D)),
	last_output(A, E),
	(   evaluation_person_visible(A, E, D)
	->  inc_eval_value(moving_hit),
	    inc_eval_value(moving_hit2),
	    inc_eval_value(moving_hit3),
	    inc_eval_value(moving_hit4)
	;   inc_eval_value(moving_miss),
	    nth0(1, B, (F, G)),
	    evaluation_person_visible(A, E, G)
	->  inc_eval_value(moving_hit2),
	    inc_eval_value(moving_hit3),
	    inc_eval_value(moving_hit4)
	;   inc_eval_value(moving_miss2),
	    nth0(2, B, (H, I)),
	    evaluation_person_visible(A, E, I)
	->  inc_eval_value(moving_hit3),
	    inc_eval_value(moving_hit4)
	;   inc_eval_value(moving_miss3),
	    nth0(3, B, (J, K)),
	    evaluation_person_visible(A, E, K)
	->  inc_eval_value(moving_hit4)
	;   inc_eval_value(moving_miss4)
	).


test_mult_camera_rule_step(A, B, C, D, E, F) :-
	(   C=<D
	->  (   mult_camera_rule(A, C, B, G)
	    ->  export(graph, C, [ (color, F), (value, G)])
	    ;   true
	    ),
	    H is C+E,
	    test_mult_camera_rule_step(A, B, H, D, E, F)
	).


stop_speaking1(A, B) :-
	person_interactivity(C, B, D),
	get_parameter(D, length, E),
	A is C+E,
	get_parameter(D, interactivity, F),
	(   F=talking
	;   F=laughing
	).


test_person_rule(A, B, C) :-
	begin(D),
	end(E),
	step(F),
	(   test_person_rule_step(A, B, D, E, F, C)
	;   true
	).


on_camera0(A, B, C, D) :-
	event_head_enter_camera(E, C, B),
	E=<A,
	not(later_event_head_leave_camera(E, A, C, B)),
	D is A-E.


print_eval_perc(A, B) :-
	eval_value(A, C),
	eval_value(B, D),
	(   C+D>0
	->  E is 100*C/ (C+D),
	    write(A),
	    write('_percent'),
	    tab(1),
	    write(E),
	    nl
	;   write(error),
	    nl
	).


person_rule(A, B, C, D, E) :-
	A=p_past_head_moving,
	rule_configuration(A, F, G, H),
	camera(D, I, J, K, L, M, N),
	step(O),
	head_moves(B, -O, F, M, C, P),
	sumlist(P, Q),
	R is Q/F,
	R>=G,
	(   R>H
	->  S is H
	;   S is R
	),
	E is (S-G)/ (H-G).
person_rule(A, B, C, D, E) :-
	A=p_future_head_moving,
	rule_configuration(A, F, G, H),
	camera(D, I, J, K, L, M, N),
	step(O),
	head_moves(B, O, F, M, C, P),
	sumlist(P, Q),
	R is Q/F,
	R>=G,
	(   R>H
	->  S is H
	;   S is R
	),
	E is (S-G)/ (H-G).
person_rule(A, B, C, D, E) :-
	A=p_future_past_head_moving,
	rule_configuration(A, F, G, H, I),
	camera(D, J, K, L, M, N, O),
	step(P),
	head_moves(B, P, G, N, C, Q),
	sumlist(Q, R),
	head_moves(B, -P, F, N, C, S),
	sumlist(S, T),
	U is (R+T)/ (G+F),
	U>=H,
	(   U>I
	->  V is I
	;   V is U
	),
	E is (V-H)/ (I-H).
person_rule(A, B, C, D, E) :-
	A=p_past_hand_moving,
	rule_configuration(A, F, G, H),
	camera(D, I, J, K, L, M, N),
	step(O),
	hand_moves(B, -O, F, M, C, P),
	sumlist(P, Q),
	R is Q/F,
	R>=G,
	(   R>H
	->  S is H
	;   S is R
	),
	E is (S-G)/ (H-G).
person_rule(A, B, C, D, E) :-
	A=p_future_hand_moving,
	rule_configuration(A, F, G, H),
	camera(D, I, J, K, L, M, N),
	step(O),
	hand_moves(B, O, F, M, C, P),
	sumlist(P, Q),
	R is Q/F,
	R>=G,
	(   R>H
	->  S is H
	;   S is R
	),
	E is (S-G)/ (H-G).
person_rule(A, B, C, D, E) :-
	A=p_future_past_hand_moving,
	rule_configuration(A, F, G, H, I),
	camera(D, J, K, L, M, N, O),
	step(P),
	hand_moves(B, P, G, N, C, Q),
	sumlist(Q, R),
	hand_moves(B, -P, F, N, C, S),
	sumlist(S, T),
	U is (R+T)/ (G+F),
	U>=H,
	(   U>I
	->  V is I
	;   V is U
	),
	E is (V-H)/ (I-H).


clear_eval_value(A) :-
	retractall(eval_value(A, B)),
	assert(eval_value(A, 0)).


test_person_rule_step(A, B, C, D, E, F) :-
	(   C=<D
	->  (   person_rule(A, C, B, G)
	    ->  export(graph, C, [ (color, F), (value, G)])
	    ;   true
	    ),
	    H is C+E,
	    test_person_rule_step(A, B, H, D, E, F)
	).


moving_virtual_camera_id(A, B) :-
	char_type(A, xdigit(C)),
	B is 200+C-10.


last_output_parametersX(A, B, C, D) :-
	findall((E, F), (output(E, F, G), E=<A), H),
	sort(H, I),
	reverse(I, J),
	nth0(0, J, (K, B)),
	output(K, B, D),
	sooner_same_camera(B, J, L, M),
	C is A-L.


get_length_step(A, B, C, D, E) :-
	(   A<B
	->  (   output(A, F, G)
	    ->  H=F
	    ;   H=D
	    ),
	    I is A+C,
	    get_length_step(I, B, C, H, J),
	    (   H<0
	    ->  E is J
	    ;   E is J+C
	    )
	;   E is 0
	).


camera_exp_base(A) :-
	A is-log(0.01).


last_output(A, B, C) :-
	last_output_parameters(A, B, C, D).


pred_last_output(A, B, C, D) :-
	once((
	    output(E, F, G),
	    E=<A
	    )),
	(   F\=B
	->  C=F,
	    D is 0
	;   once((
		output(H, C, I),
		H=<E,
		C\=F
		))
	->  findall(J, J^K^ (output(J, F, K), J>H, J=<E), L),
	    last(L, M),
	    D is A-M
	;   fail
	).


init_moving_virtual_cameras(A) :-
	rule_configuration(s_moving_virtual_cameras, B, C, D, E, F, G),
	step(H),
	ignore(forall(person(I), forall((camera(J, K, L, M, N, O, P), J==O), ignore((moving_virtual_camera_id(I, Q), head_full_positions(A, 1, E, O, I, R), head_full_positions(A, -1, D, O, I, S), append(S, R, T), findall(U, member((U, V, W, X, Y, Z), T), A1), findall(B1, member((C1, D1, E1, B1, F1, G1), T), H1), averlist(A1, I1), averlist(H1, J1), K1 is M/B/2, L1 is N/B/2, M1 is L1*C, (last_moving_virtual_camera(A, O, Q, N1, O1, P1)->Q1 is P1-M1, R1 is A+F, head_full_positions(R1, 1, E, O, I, S1), head_full_positions(R1, -1, D, O, I, T1), append(T1, S1, U1), findall(U, member((U, V1, W1, X1, Y1, Z1), U1), A2), findall(B1, member((B2, C2, D2, B1, E2, F2), U1), G2), averlist(A2, H2), averlist(G2, I2), J2 is O1+ (H2-O1)/ (F/H), K2 is Q1+ (I2-Q1)/ (F/H), (H2-I1)^2+ (I2-J1)^2> (G*F)^2, U is round(min(max(K+K1, J2), K+M-K1)), B1 is round(min(max(L+L1, K2+M1), L+N-L1)), (O1==U, P1==B1, N1==B->fail;true), retractall(moving_virtual_camera(A, O, Q, L2, M2, N2)), assert(moving_virtual_camera(A, O, Q, B, U, B1));J2 is I1, K2 is J1, U is round(min(max(K+K1, J2), K+M-K1)), B1 is round(min(max(L+L1, K2+M1), L+N-L1)), retractall(moving_virtual_camera(A, O, Q, O2, P2, Q2)), assert(moving_virtual_camera(A, O, Q, B, U, B1)))))))).


generate_all_head_move(A, B) :-
	forall((bagof(C, get_head_move(A, -B, D, E, C), F), averlist(F, G)), assert(head_move(A, D, E, G))).


import_step_internal :-
	forall(event_head(A, B), (get_parameter(B, camera, C), get_parameter(B, object, D), get_parameter(B, centerx, E), get_parameter(B, centery, F), get_parameter(B, minx, G), get_parameter(B, miny, H), get_parameter(B, maxx, I), get_parameter(B, maxy, J), get_parameter(B, person, K), assert(head(A, C, D, E, F, G, H, I, J, K)))),
	forall(event_hand(A, B), (get_parameter(B, camera, C), get_parameter(B, object, D), get_parameter(B, centerx, E), get_parameter(B, centery, F), get_parameter(B, minx, G), get_parameter(B, miny, H), get_parameter(B, maxx, I), get_parameter(B, maxy, J), get_parameter(B, person, K), assert(hand(A, C, D, E, F, G, H, I, J, K)))),
	forall(event_start_speaking(A, B), (get_parameter(B, person, K), assert(start_speaking(A, K)))),
	forall(event_stop_speaking(A, B), (get_parameter(B, person, K), assert(stop_speaking(A, K)))),
	init_import.


generate_fixed_virtual_cameras :-
	ignore(forall(rule_configuration(s_fixed_virtual_cameras, A, B, C, D, E), assert(virtual_camera(A, B, C, D, E)))).


evaluate_output_step(A, B, C, C, []).
evaluate_output_step(A, B, C, D, [E|F]) :-
	(   output_rule(E, A, B, C, G)
	->  evaluate_output_step(A, B, G, D, F)
	;   evaluate_output_step(A, B, C, D, F)
	).


init_persons :-
	retractall(person_count(A)),
	(   rule_configuration(s_mode, offline)
	->  ignore(generate_all_persons)
	;   true
	),
	findall(B, person(B), C),
	length(C, D),
	assert(person_count(D)).


last_output_optimized(A, B) :-
	last_output_actual(A, B, C).


set_virtual_camera_time(A) :-
	ignore(forall((virtual_camera(B, C, D, E, F), is_moving_virtual_camera_id(C)), retractall(virtual_camera(B, C, D, E, F)))),
	ignore(forall((camera(G, H, I, J, K, B, L), B==G), forall(person(M), (moving_virtual_camera_id(M, C), last_moving_virtual_camera(A, G, C, D, E, F)->assert(virtual_camera(G, C, D, E, F));true)))).


export_virtual_camera_rectangles :-
	begin(A),
	end(B),
	step(C),
	(   export_virtual_camera_rectangles_step(A, B, C)
	;   true
	).


evaluation_head_moving(A, B, C, D) :-
	E is 5000,
	F is 5000,
	camera(C, G, H, I, J, K, L),
	step(M),
	head_moves(A, M, F, K, B, N),
	head_moves(A, -M, E, K, B, O),
	sumlist(N, P),
	sumlist(O, Q),
	D is (P+Q)/ (F+E).


rule_configuration(unused_rule_name, value1, value2).
rule_configuration(s_person_visible_window, 2000, 0).
rule_configuration(s_person_mult, a, 1).
rule_configuration(s_person_mult, b, 1).
rule_configuration(s_person_mult, c, 1).
rule_configuration(s_person_mult, d, 1).
rule_configuration(c_anti_quick, 2000, 38000).
rule_configuration(c_anti_lazy, 10000, 30000).


evaluate_cameras(A, B) :-
	ignore((
	    (   not(rule_configuration(s_mode, offline))
	    ->  generate_person_activity(A)
	    )
	    )),
	update_last_output_optimized(A),
	update_model_state(A),
	set_virtual_camera_time(A),
	bagof(C, camera(C), D),
	evaluate_cameras(A, D, B).


evaluation_tech_step(A, B, C) :-
	(   A=<B
	->  set_virtual_camera_time(A),
	    findall(D, evaluate_tech(A), E),
	    F is A+C,
	    evaluation_tech_step(F, B, C)
	).


minlist([A], B) :-
	B is A.
minlist([A|B], C) :-
	minlist(B, D),
	(   D<A
	->  C is D
	;   C is A
	).


camera(A, B, C, D, E) :-
	camera(A, B, C, D, E, F, G).


print_eval_perc2(A, B) :-
	eval_value(B, C),
	findall(D, (member(E, A), eval_value(E, D)), F),
	sumlist(F, G),
	(   C>0
	->  H is 100*G/C,
	    write(B),
	    write('_percent'),
	    tab(1),
	    write(H),
	    nl
	;   write(error),
	    nl
	).


get_head_move(A, B, C, D, E) :-
	head(A, C, F, D, G, H),
	I is A+B,
	head(I, C, F, D, J, K),
	E is sqrt((J-G)**2+ (K-H)**2).


find_best_camera(A, B) :-
	evaluate_cameras(A, C),
	find_max_cameras(C, D),
	length(D, E),
	(   E=:=0
	->  fail
	;   E=:=1
	->  nth0(0, D, (B, F))
	;   last_output_optimized(A, G),
	    member((G, H), D)
	->  B=G
	;   I is 0,
	    nth0(I, D, (B, J))
	).


get_length(A) :-
	begin(B),
	end(C),
	step(D),
	get_length_step(B, C, D, -1, A).


last_output_optimized(A, B, C) :-
	(   last_output_actual(A, B, C)
	->  true
	;   last_output(A, B, C)
	).


last_moving_virtual_camera(A, B, C, D, E, F) :-
	findall((G, D, E, F), (moving_virtual_camera(G, B, C, D, E, F), G=<A), H),
	sort(H, I),
	last(I, (J, D, E, F)).


is_moving_virtual_camera_id(A) :-
	A mod 10000>=200.


import_step :-
	set_prolog_flag(unknown, warning),
	ignore(import_step_internal),
	set_prolog_flag(unknown, error).
