#include "library.h" struct actor { double x, y, spd, reach; int size, color; bool alive, safe; string result; }; struct universe { actor boy, bull, tree, dinosaur; int fieldw, fieldh, edge; }; universe u; void set_field(int w, int h, int e) { u.fieldw = w; u.fieldh = h; u.edge = e; } void set(actor & A, double x, double y, double s, double r) { A.x = x; A.y = y; A.spd = s; A.reach = r; A.alive = true; A.safe = false; A.size = 25; A.color = color::magenta; A.result = "You didn't set me!"; } void set_sz_color_string(actor & A, int sz, int c, string r) { A.size = sz; A.color = c; A.result = r; } void draw_to(actor A) { draw_to(u.edge+A.x, u.edge+A.y); } void move_to(actor A) { move_to(u.edge+A.x, u.edge+A.y); } void draw_actor(actor A) { set_pen_color(A.color); set_pen_width(A.size); draw_point(A.x+u.edge, A.y+u.edge); } void draw_field() { set_pen_color(color::green); move_to(u.edge, u.edge); draw_to(u.edge+u.fieldw, u.edge); draw_to(u.edge+u.fieldw, u.edge+u.fieldh); draw_to(u.edge, u.edge+u.fieldh); draw_to(u.edge, u.edge); } void draw_actors() { draw_actor(u.tree); draw_actor(u.boy); draw_actor(u.bull); draw_actor(u.dinosaur); } bool close_enough(double ax, double ay, double bx, double by, double reach) { double dist = sqrt((ax-bx)*(ax-bx) + (ay-by)*(ay-by)); return dist < reach; } bool close_enough(actor mover, actor target) { return close_enough(mover.x, mover.y, target.x, target.y, mover.reach); } // move the mover, draw the line, return whether reached target or not bool move_towards(actor & mover, actor target, double deltat) { if (! mover.alive) return false; double dir = atan2(target.y-mover.y, target.x-mover.x); double dist = mover.spd * deltat; double dx = dist * cos(dir); double dy = dist * sin(dir); move_to(mover); set_pen_color(mover.color); mover.x += dx; mover.y += dy; draw_to(mover); return close_enough(mover, target); } bool perform_one_step(actor & mover, actor & target, double deltat) { bool reached_target = move_towards(mover, target, deltat); if (reached_target && target.alive && ! target.safe) { write_string(mover.result); target.alive = false; } return reached_target; } void main() { set_field(700, 500, 50); set(u.tree, 350, 450, 0, 0); set(u.bull, 700, 0, 5, 5); set(u.boy, 0, u.fieldh, 3, 2); set(u.dinosaur, u.fieldw, u.fieldh, 7, 2); set_sz_color_string(u.boy, 4, color::blue, "Safe!"); set_sz_color_string(u.bull, 4, color::red, "Boy Eaten"); set_sz_color_string(u.tree, 8, color::brown, "Yor program is wrong"); set_sz_color_string(u.dinosaur, 6, color::dark_green, "Graaaaaaah!"); double deltat=0.002; bool boysafe=false; make_window(u.fieldw+2*u.edge, u.fieldh+2*u.edge); draw_field(); draw_actors(); for (double t=0.0; true; t+=deltat) { bool reached = perform_one_step(u.boy, u.tree, deltat); if (reached) u.boy.safe = true; perform_one_step(u.bull, u.boy, deltat); if (u.bull.alive) perform_one_step(u.dinosaur, u.bull, deltat); else perform_one_step(u.dinosaur, u.boy, deltat); } }