// By Chung-Chih Li, Nov. 19, 2002 // This program uses CMU Graphics library. #include using namespace std; #include #include int W_Width=1000; const double PI = 3.141592653589793238462643383279; class point { friend class triangle; public: point(); point(double x, double y); double x() const; double y() const; double distance(point & p) const; private: double my_x; double my_y; }; class triangle { public: triangle(); triangle(point a, point b, point c); point p1(); point p2(); point p3(); void set_color(int color); void shift(point v); double area(); point center(); triangle rotate(double theta); // use default center triangle rotate(double theta, point C); // use c as center; void shift(point v); private: point my_p1; point my_p2; point my_p3; int my_color; point rotate_oneP(double theta, point P, point center); }; point::point() :my_x(0), my_y(0) { } point::point(double x, double y) :my_x(x), my_y(y) { } double point::x() const { return my_x; } double point::y() const { return my_y; } double point::distance(point & p) const { return sqrt(pow(my_x-p.my_x,2)+pow(my_y-p.my_y,2)); } triangle::triangle() :my_p1(point(0,0)), my_p2(point(0,0)), my_p3(point(0,0)),my_color(0) {} triangle::triangle(point a, point b, point c) :my_p1(a), my_p2(b), my_p3(c),my_color(0) {} point triangle::p1() { return my_p1; } point triangle::p2() { return my_p2; } point triangle::p3() { return my_p3; } void triangle::shift(point v) { my_p1.my_x += v.x(); my_p1.my_y += v.y(); my_p2.my_x += v.x(); my_p2.my_y += v.y(); my_p3.my_x += v.x(); my_p3.my_y += v.y(); } double triangle::area() { double a,b,c,s,Area; a = my_p1.distance(my_p2); b = my_p2.distance(my_p3); c = my_p3.distance(my_p1); s = (a+b+c)/2; Area = sqrt(s*(s-a)*(s-b)*(s-c)); return Area; } point triangle::center() { double x,y; x = (my_p1.my_x+my_p2.my_x+my_p3.my_x)/3.0; y = (my_p1.my_y+my_p2.my_y+my_p3.my_y)/3.0; return point(x,y); } void triangle::set_color(int color) { my_color=color; } triangle triangle::rotate(double theta) // use default center { point C = center(); my_p1 = rotate_oneP(theta, my_p1, C); my_p2 = rotate_oneP(theta, my_p2, C); my_p3 = rotate_oneP(theta, my_p3, C); return triangle(my_p1,my_p2,my_p3); } triangle triangle::rotate(double theta, point C) // use c as center; { my_p1 = rotate_oneP(theta, my_p1, C); my_p2 = rotate_oneP(theta, my_p2, C); my_p3 = rotate_oneP(theta, my_p3, C); return triangle(my_p1,my_p2,my_p3); } point triangle::rotate_oneP(double theta, point P, point C) { double x = P.x() - C.x(); double y = P.y() - C.y(); double r = P.distance(C); double beta; if ( x<= 0.0000001 && x >= -0.0000001) beta=3.1415926/2; else beta = atan(y/x); if (x < -0.0000001) beta = beta+3.1415926; beta -= theta; x = r*cos(beta); y = r*sin(beta); return point(x+C.x(),y+C.y()); } void drawT(window *W, triangle T) { W->DrawLine(T.p1().x(), T.p1().y(), T.p2().x(), T.p2().y()); W->DrawLine(T.p2().x(), T.p2().y(), T.p3().x(), T.p3().y()); W->DrawLine(T.p3().x(), T.p3().y(), T.p1().x(), T.p1().y()); // W->DrawLine(T.center().x(), T.center().y(), T.center().x()+1, T.center().y()+1); } void main() { window *GWin; int x,y; int Font_size = 20, GWin_X_Width, GWin_Y_Width; double theta; cout << "Input Window Width (400-2800):"; cin >> x; // x= 600; W_Width=x; GWin_X_Width=W_Width; GWin_Y_Width= GWin_X_Width*3/4; point a(0,GWin_Y_Width-20); point b(GWin_X_Width/5,GWin_Y_Width-GWin_X_Width/10); point c(GWin_X_Width/4,GWin_Y_Width-20); triangle Tri(a,b,c); cout << "Click on the " << GWin_X_Width << "X" << GWin_Y_Width << " Window to activate." << endl; window LocalWin(GWin_X_Width, GWin_Y_Width, 0, 0); GWin = &LocalWin; GWin->SetWaitClose(false); GWin->ChangeTitle("Rotation in CMU Graphics Windows C.C.L."); GWin->WaitMouseClick(x,y); x=y=0; GWin->SetFont(Font_size,1,ROMAN); GWin->SetPen(0.0, 0.0, 1.0); GWin->SetFont(Font_size,1,ROMAN); drawT(GWin, Tri); GWin->WaitMouseClick(x,y); x=y=0; double g=-0.01, steps=500; double hv = GWin_X_Width/steps; double vv= -g*(GWin_X_Width/3), vs=0; double d_theta = -0.05; point s; double i=0; while (Tri.center().y() <= GWin_Y_Width-20) { i = i+hv; s = point(hv,vs-(vv*i+g*i*i/2)); vs = (vv*i+g*i*i/2); Tri.shift(s); Tri.rotate(d_theta); drawT(GWin, Tri); GWin->GetMouseClick(x,y); if ( x >= 0) { Sleep(20); GWin->WaitMouseClick(x,y); } else Sleep(20); } GWin->WaitMouseClick(x,y); }