Chủ Nhật, 26 tháng 4, 2015

Hướng dẫn sử dụng thư viện đồ hoạ trong C/C++ hay BC


1. Yêu cầu
Phi có tp tin điu khin màn hình EGAVGA.BGI (thông thường tp này thường nm
trong thư mc \BC\BGI hay TC\BGI khi cài đt).
Nếu chúng ta có s dng ti font ch thì cn phi có thêm các file (*.CHR) như:
GOTH.CHR (ch Gothic), LITT.CHR (ch Small Font), SANS.CHR (ch Sans Serif),
TRIP.CHR (ch cao gp 3).
Đ dùng được thư vin các hàm đ ho cn có dòng lnh:
#include <graphics.h> và đt mc chn Graphics library là ON ([x] trong menu
Options/Linker/Libraries.
Khi cn tham kho cú pháp, cách s dng ca bt kỳ mt hàm đ ho nào, đưa con tr v
tên hàm trong chương trình sau đó nhn t hp phím CTRL+F1. Mun tham kho danh sách toàn
b các hàm ca thư vin đ ho nhn t hp phím CTRL+F1 ngay ti dòng ch <graphics.h>.
2. Khởi tạo và đóng chế độ đồ hoạ
Đ phân gii ca màn hình được đo bng s đim theo chiu ngang nhân vi s đim theo
chiu dc ca màn hình đ ho. To đ gc ca màn hình đ ho (0,0) là đim nm ti góc trên
cùng phía bên trái. Mi kiu đ ho dùng mt h to đ riêng. H to đ cho màn hình VGA là
640x480.
Khi đng đ ho vi màn hình ngm đnh:
#include <graphics.h>
void main(void){
int gdriver, gmode, errocode;
gdriver = DETECT;//ngầm định
initgraph(&gdriver,&gmode,”C:\TC\BGI“); //tìm mode màn hình trong thư mục BGI
errorcode = graphresult();
if (errorcode !=grOk) {
printf(“\n Không khởi tạo được”);
getch();exit(1);
}
...................// Các thao tác đồ hoạ tiếp theo
closegraph();
}
Ví d: viết chương trình hai đường thng ct nhau
#include <conio.h>
#include <graphics.h>
#include <math.h>
// hệ số đổi từ độ sang radian
Ph lc 1
143
#define RADS 0.017453293
void giaodiem(double x1, double y1, double x2, double y2,
double a1, double b1, double a2, double b2) {
double dx, dy, da, db, x, y, t, tich;
dx = x2 - x1;
dy = y2 - y1;
da = a2 - a1;
db = b2 - b1;
tich = db * dx - da * dy;
if (tich != 0) {
t = ((a1 - x1) * dy - (b1 - y1) * dx) / tich;
if (t>=0.0 && t<=1.0) {
x = t * (a2 - a1) + a1;
y = t * (b2 - b1) + b1;
line(x1, y1, x2, y2);
line(a1, b1, a2, b2);
setfillstyle(SOLID_FILL, RED);
fillellipse(x, y, 3, 3);
}
}
}
void main() {
int gr_drive = DETECT, gr_mode;
double x1, y1, x2, y2, a1, b1, a2, b2;
printf("\nNhap vao toa do doan thang thu nhat: ");
scanf("%lf%lf%lf%lf", &x1, &y1, &x2, &y2);
printf("\nNhap vao toa do doan thang thu hai: ");
scanf("%lf%lf%lf%lf", &a1, &b1, &a2, &b2);
initgraph(&gr_drive, &gr_mode, "");
giaodiem(x1, y1, x2, y2, a1, b1, a2, b2);
getch();
closegraph(); //đóng chế độ đồ hoạ
}
3. Các hàm cơ bản
3.1. Bảng màu của màn hình đồ hoạ.
Setbkcolor(int color) thiết lp màu nn cho màn hình đ ho
setcolor(int color) đt màu v cho nét v hin ti
getmaxcolor() ly s màu cao nht được s dng trong chế đ đ ho hin ti
setallpalette(struct palettetype far
*palette)
s làm thay đi toàn b màu trong bng màu palette
setpalette( int colox, int colory) s làm thay đi màu th colorx thành màu colory
getpalette(struct palettetype far
*palette)
s ly li giá tr ca palette đang dùng
textheight(“W”) ly chiu cao ca dòng văn bn
Ph lc 1
144
outextxy(int x, int y, char * msg) Ch th đưa xâu kí t msg ra màn hình đ ho ti v trí (x,y)
3.2. Nguyên sơ điểm
Nguyên sơ đơn gin nht chính là đim, mi nguyên sơ khác đu được xây dng nên t
đim.
int getmaxx() S chm đim ln nht theo chiu ngang trong chế đ đ ho hin ti
int getmaxy() S chm đim ln nht theo chiu dc trong chế đ đ ho hin ti
putpixel( x, y, color) Đ v mt đim sáng lên màn hình ti đim (x, y) có màu color
getpixel(x,y) nhn biết màu hin ti ca đim (x, y)
3.3. Nguyên sơ đường
Các hàm cho đường:
moveto(int x, int y) di chuyn v trí con tr hin ti ca màn hình đ ho ti to đ (x,y)
getx(), gety() ly to đ ca con tr hin ti theo chiu ngang và chiu dc màn hình đ
ho
lineto(int x, int y) v mt đường thng t v trí con tr hin ti ti v trí có to đ (x, y) trên
màn hình đ ho
line(int x1, int y1, int x2,
int y2)
V mt đường thng t to đ (x1,y1) đến to đ (x2, y2) trên màn hình
đ ho. Đường thng mi được v không ph thuc vào v trí hin thi ca
con tr màn hình
linerel(int dx, int dy) V mt đon thng t v trí con tr hin ti ti v trí (x +dx, y+dy). Sau khi
v con tr chuyn ti v trí mi (x+dx, y+dy)
3.4. Nguyên sơ hình chữ nhật
rectangle(int x1, int y1, int x2, int y2) v hình ch nht có to đ phía góc trên bên trái là
(x1, y1) và góc dưới bên phi có to đ (x2,y2).
bar(int x1, int y1, int x2, int y2) v hình ch nht có tô màu phía trong. Hai ch th rectangle
và bar khác nhau ch rectangle ch to nên mt hình ch nht vi đường vin bao quanh.
bar3d(int x1,int y1,int x2,int y2,int depth, int top) v khi hp ch nht, mt ngoài ca nó là
hình ch nht xác đnh bi các to đ (x1,y1,x2,y2) hình ch nht này được tô màu, depth là
chiu sâu ca khi 3 chiu, top nhn giá tr 1 hoc 0 đ khi 3 chiu có np hay không có np.
3.5. Nguyên sơ hình tròn
Tt c các hàm dưới đây, góc tính theo đ và giá tr t 00 đến 3600 .
arc(int x, int y, int gd,int gc,int r) v cung tròn có (x,y) ta đ tâm tròn, r bán kính, gd góc
đu, gc góc cui.
circle( int x, int y, int r) là hàm v hình tròn có tâm ti đim (x,y) vi bán kính r.
ellipse(int x, int y,int gd, int gc,int xr, int yr) v 1 hình ellipse có (x,y) to đ tâm cung, gd
góc đu, gc góc cui, xr là bán trc ngang, yr là bán trc đng.
Ph lc 1
145
pieslice(int x, int y, int gd, int gc, int r) v và tô màu hình qut có (x,y) là to đ tâm qut,
gd là góc đu, gc là góc cui, r là bán kính.
3.6. Nguyên sơ đa giác
drawpoly(int numpoints, int far *polypoints) s v nên mt đường gp khúc bt kỳ vi
numpoints là s đim mà đường gp khúc đi qua, polypoints (mng) to đ đim (x1,y1,x2,y2....).
Khi đim cui (xn,yn) trùng vi đim đu (x1,y1) thì được mt đa giác.
fillpoly(int numpoints, int *polypoints) s tô màu đa giác bng màu hin thi.
setfillstyle(int pattern, int color) dùng đ xác đnh mu tô cho đa giác, trong đó mu tô là
các hng s nguyên được đnh nghĩa như sau:
Tên hng mu Giá tr Mô t
EMPTY_FILL 0 Tô bng màu nn
SOLID_FILL 1 Tô bng nét lin
LINE_FILL 2 Tô ------
LTSLASH_FILL 3 Tô ////
SLASH_FILL 4 Tô ///// in đm
BKSLASH_FILL 5 Tô \\\\\ in đm
LTBKSLASH_FILL 6 Tô \\\\
HATCH_FILL 7 Tô đường gch bóng nht
XHATCH_FILL 8 Tô đường gch bóng ch thp
INTERLEAVE_FILL 9 Tô đường đt quãng
WIDE_DOT_FILL 10 Tô bng du chm thưa
CLOSE_DOT_FILL 11 Tô bng du chm dày
3.7. Nguyên sơ văn bản
outtext( char far *textstring) s hin th ni dung xâu textstring ti v trí hin thi ca màn
hình đ ho.
outtextxy(int x, int y, char far *textstring) hin th ni dung xâu textstring ti to đ (x, y)
trong màn hình đ ho.
settextstyle(int font, int direction, int charzise) dùng đ xác lp kiu ch vi các font ch
khác nhau.
Trong đó int font được xác lp thông qua các hng sau:
TÊN FONT Giá tr Ý nghĩa
DEFAULT_FONT 0 Font 8x8 bit-mapped
TRIPLEX_FONT 1 Stroked triplex font
Ph lc 1
146
SMALL_FONT 2 Stroked small font
SANS_SERIF_FONT 3 Stroked sans-serif font
GOTHIC_FONT 4 Stroked gothic font
int direction được xác đnh nếu HORIZ_DIR = 0 là nm ngang t trái qua phi, VERT_DIR
=1 là thng đng t dưới lên trên.
int charsize nhn giá tr t 1 đến 10 là h s phóng đi ch.
settextjustification( int hoz, int vert) xác đnh v trí dòng văn bn được đưa ra màn hình đ
ho bi outtext() và outtextxy().
Trong đó int hoz có th nhn mt trong các hng sau:
LEFT_TEXT =0 văn bn xut hin phía bên trái con tr màn hình đ ho
CENTER_TEXT =1 văn bn xut hin gia vi tâm là con tr màn hình đ ho
RIGHT_TEXT =2 văn bn xut hin phía bên phi con tr màn hình đ ho
Còn int vert là tham s có th nhn các giá tr sau:
BOOTTOM_TEXT=0 văn bn xut hin phía trên con tr
CENTER_TEXT=1 văn bn xut hin quanh con tr
TOP_TEXT=2 văn bn xut hin phía dưới con tr
textheight(char *s) tr v chiu cao (theo pixel) ca chui do s tr ti. Vi 8x8 bit map Font
và h s khuyếch đi ch là 1 thì textheight(“H”)=8
textwidth(char *s) tr v chiu dài ca chui tính theo pixel.
3.8. Cửa sổ (viewport)
viewport là 1 vùng hình ch nht trên màn hình đ ho ging như window trong textmode.
setviewport(int x1, int y1, int x2, int y2, int clip) trong đó (x1,y1,x2,y2) là góc trái trên và
góc phi dưới tho mãn điu kin như sau:
0<=x1 <= x2 và 0<= y1 <= y2
Tham s clip: clip=1 không cho phép v ra ngoài viewport
clip=0 cho phép v ra ngoài viewport
getviewsettings(struct viewporttype *vp) nhận viewport hiện hành,
struct viewporttype {
int left,top,right,bottom;
int clip;
};
clearviewport(void) xoá viewport
cleardevice(void) xoá mi th trên màn hình và đưa con tr v to đ (0,0) ca màn hình
Chú ý: nh s dng viewport ta có th viết các chương trình đ ho có trc to đ, bng
cách thiết lp viewport vi clip=0 (cho phép v ra ngoài gii hn)
3.9. Tạo hình ảnh chuyển động
Nguyên sơ mi mà chúng ta s xây dng là to hình nh chuyn đng trên màn hình đ ho.
V nguyên tc, đ có th to nên nhng hình nh chuyn đng chúng ta cn có mt hình mu, sau
Ph lc 1
147
đó lưu hình mu trên màn hình đ ho li bng ch th getimage(int x1, int y1, int x2, int y2, void
far *bitmap); trong đó bitmap là min nh dùng đ lưu hình nh ca hình ch nht có to đ
(x1,y1) và (x2, y2) trên màn hình đ ho.
Ch th getimagesize(int x1, int y1, int x2, int y2) dùng đ xác đnh kích thước b nh dùng
đ ct hình nh gii hn trong hình ch nht có to đ (x1, y1), (x2,y2).
Ch th putimage(int x, int y, void far * bitmap, int copymode) dùng đ khôi phc li hình
nh đã được ct gi bng getimage(). Ch th putimage() kết hp vi ch th làm tr (delay() ) sao
cho s các hình nh hin th trên màn hình đ ho khong 24 hình/giây chúng ta s nhn được mt
hình nh chuyn đng.
Ví d 1: To hình nh chuyn đng là mt mũi tên.
#include <graphics.h>
#include <stdlib.h>
#include <stdio.h>
#include <conio.h>
#define ARROW_SIZE 10
void draw_arrow(int x, int y);
int main(void) {
/* request autodetection */
int gdriver = DETECT, gmode, errorcode;
void *arrow;
int x, y, maxx;
unsigned int size;
/* initialize graphics and local variables */
initgraph(&gdriver, &gmode, "\\TC\\BGI");
/* read result of initialization */
errorcode = graphresult();
if (errorcode != grOk) { /* an error occurred */
printf("Graphics error: %s\n", grapherrormsg(errorcode));
printf("Press any key to halt:");
getch();
exit(1); /* terminate with an error code */
}
maxx = getmaxx(); x = 0;
y = getmaxy() / 2;
/* draw the image to be grabbed */
draw_arrow(x, y);
/* calculate the size of the image */
size = imagesize(x, y-ARROW_SIZE, x+(4*ARROW_SIZE), y+ARROW_SIZE);
/* allocate memory to hold the image */
arrow = malloc(size);
/* grab the image */
getimage(x, y-ARROW_SIZE, x+(4*ARROW_SIZE), y+ARROW_SIZE, arrow);
/* repeat until a key is pressed */
Ph lc 1
148
while (!kbhit()){
/* erase old image */
putimage(x, y-ARROW_SIZE, arrow, XOR_PUT);
x += ARROW_SIZE;
if (x >= maxx)
x = 0;
/* plot new image */
putimage(x, y-ARROW_SIZE, arrow, XOR_PUT);
}
/* clean up */
free(arrow);
closegraph();
return 0;
}
void draw_arrow(int x, int y) {
/* draw an arrow on the screen */
moveto(x, y);
linerel(4*ARROW_SIZE, 0);
linerel(-2*ARROW_SIZE, -1*ARROW_SIZE);
linerel(0, 2*ARROW_SIZE);
linerel(2*ARROW_SIZE, -1*ARROW_SIZE);
}
Các code chương trình ví dụ cho bài tập lập trình
Bài 1: quay đối tượng
#include<stdio.h>
#include<dos.h>
#include<conio.h>
#include<graphics.h>
#include<stdlib.h>
#include<math.h>
#include<alloc.h>
#define RADS 0.017453293
struct point{
int x,y,z;
}
a[4]=
{
{110,180,80},
{10,200,80},
{120,50,80},
{110,180,250}
};
int noi[4][4];
void Bresenham_Line(int x1,int y1, int x2, int y2, int c)
{
Ph lc 1
149
if(x1 == x2)
{
int i;
if(y1 < y2)
for(i = y1; i <= y2;i ++)
{
putpixel(x1,i,c); delay(10);
}
else
for(i = y2; i<= y1; i ++)
{
putpixel(x1,i,c); delay(10);
}
}
if(y1 == y2)
{
int i;
if(x1 < x2)
for(i = x1; i <= x2; i ++)
{
putpixel(i,y1,c);delay(10);
}
else
for(i = x2; i <= x1; i ++)
{
putpixel(i,y1,c); delay(10);
}
}
if(x1 < x2)
{
if(y1 < y2)
{
if((y2 - y1)/(x2-x1) < 1)
{
int i;
int Dx = x2 - x1;
int Dy = y2 - y1;
int p = 2*Dy - Dx;
putpixel(x1,y1,c);
for(i = x1; i < x2; i ++)
{
if(p < 0)
p += 2*Dy;
else
{
p += 2*(Dy - Dx);
y1 ++;
}
x1 ++;
putpixel(x1,y1,c); delay(10);
Ph l__________c 1
150
}
}
else
{
int i;
int Dx = x2 - x1;
int Dy = y2 - y1;
int p = 2*Dx - Dy;
putpixel(x1,y1,c);
for(i = y1; i < y2; i ++)
{
if(p < 0)
p += 2*Dx;
else
{
p += 2*(Dx - Dy);
x1 ++;
}
y1 ++;
putpixel(x1,y1,c); delay(10);
}
}
}
if(y1 > y2)
{ if((y2 - y1)/(x2 - x1)> -1 )
{
int i;
int Dx = x2 - x1;
int Dy = y2 - y1;
int p = 2*Dy + Dx;
putpixel(x1,y1,c);
for(i = x1; i <= x2; i ++)
{
if(p > 0)
p += 2*Dy;
else
{
p += 2*(Dy + Dx);
y1-- ;
}
x1 ++;
putpixel(x1,y1,c); delay(10);
}
}
else
{
int i;
int Dx = x2 - x1;
int Dy = y2 - y1;
int p = 2*Dx + Dy;
Ph lc 1
151
putpixel(x1,y1,c);
for(i = y1; i >= y2; i --)
{
if(p < 0)
p += 2*Dx;
else
{
p += 2*(Dx + Dy);
x1++ ;
}
y1 --;
putpixel(x1,y1,c); delay(10);
}
}
}
}
if(x1 > x2)
{
if(y1 < y2)
{ if((y2-y1)/(x2-x1) > -1)
{
int i;
int Dx = x2 - x1;
int Dy = y2 - y1;
int p = -2*Dy - Dx;
putpixel(x1,y1,c);
for(i = x1; i > x2; i --)
{
if(p < 0)
{
p=p - 2*Dy - 2*Dx;
y1 ++;
}
else
p =p - 2*Dy;
x1 --;
putpixel(x1,y1,c);delay(10);
}
}
else
{
int i;
int Dx = x2 - x1;
int Dy = y2 - y1;
int p = -2*Dx - Dy;
putpixel(x1,y1,c);
for(i = y1; i < y2; i ++)
{
if(p < 0)
p -= 2*Dx;
Ph lc 1
152
else
{
p -= 2*(Dx + Dy);
x1 --;
}
y1 ++;
putpixel(x1,y1,c); delay(10);
}
}
}
if(y1 > y2)
{
if((y2-y1)/(x2-x1) < 1)
{
int i;
int Dx = x2 - x1;
int Dy = y2 - y1;
int p = 2*Dy - Dx;
putpixel(x1,y1,c);
for(i = x1; i > x2; i --)
{
if(p > 0)
{
p =p - 2*Dy +2*Dx ;
y1--;
}
else
p -= 2*Dy;
x1 --;
putpixel(x1,y1,c); delay(10);
}
}
else
{
int i;
int Dx = x1 - x2;
int Dy = y1 - y2;
int p = 2*Dx + Dy;
putpixel(x1,y1,c);
for(i = y1; i > y2; i --)
{
if(p < 0)
{
p =p - 2*Dx + 2*Dy ;
x1 --;
}
else
Ph lc 1
153
p =p - 2*Dx ;
y1 --;
putpixel(x1,y1,c); delay(10);
}
}
}
}
}
void Dothi()
{
Bresenham_Line(getmaxx()/2,getmaxy()/2,getmaxx()-10,getmaxy()/2,15);
Bresenham_Line(getmaxx()/2,10,getmaxx()/2,getmaxy()/2,15);
Bresenham_Line(getmaxx()/2,getmaxy()/2,getmaxx()/2-170,getmaxy()/2+170,15);
Bresenham_Line(getmaxx()/2-170,getmaxy()/2+170,getmaxx()/2-170,getmaxy()/2+166,15);
Bresenham_Line(getmaxx()/2-170,getmaxy()/2+170,getmaxx()/2-163,getmaxy()/2+167,15);
settextjustify(CENTER_TEXT,CENTER_TEXT);
outtextxy(getmaxx()-9,getmaxy()/2+1,"_");
outtextxy(getmaxx()-9,getmaxy()/2+10,"y");
outtextxy(getmaxx()/2,10,"-");
outtextxy(getmaxx()/2 - 10,10,"z");
outtextxy(getmaxx()/2-155,getmaxy()/2+170,"x");
}
point Diem3d(int x , int y , int z)
{
point p;
if(x>=0&&y>=0&&z>=0)
{
p.x = int(getmaxx()/2+y - x*cos(RADS*45));
p.y = int(getmaxy()/2-z + x*cos(RADS*45));
}
if(y>=0&&x<0&&z>=0)
{
p.x = int(y+getmaxx()/2-x*cos(RADS*45));
p.y = int(getmaxy()/2-z+x*cos(RADS*45));
}
if(x>=0&&y<0&&z>=0)
{
p.x = int(getmaxx()/2+y-x*cos(RADS*45));
p.y = int(getmaxy()/2-(z-x*cos(RADS*45)));
}
if(x>=0&&y>=0&&z<0)
{
p.x = int(getmaxx()/2+y-x*cos(RADS*45));
p.y = getmaxy()/2-z+x*cos(RADS*45);
}
if(y>=0&&x<0&&z<0)
{
p.x = int(getmaxx()/2+y-x*cos(RADS*45));
p.y = int(getmaxy()/2+(-z-x*cos(RADS*45)));
Ph lc 1
154
}
if(x>=0&&y<0&&z<0)
{
p.x = int(getmaxx()/2+y-x*cos(RADS*45));
p.y = int(getmaxy()/2-z+x*cos(RADS*45));
}
if(z>=0&&y<0&&x<0)
{
p.x = int(getmaxx()/2-(-y+x*cos(RADS*45)));
p.y = int(getmaxy()/2-(z-x*cos(RADS*45)));
}
if(x<0&&y<0&&z<0)
{
p.x = int(getmaxx()/2+y-x*cos(RADS*45));
p.y = int(getmaxy()/2-z+x*cos(RADS*45));
}
return(p);
}
point hinhchieu(int &x, int &y , int &z , int chieu)
{
point p;
if(chieu==1)
{
p.x =int( getmaxx()/2+y - x*cos(RADS*45));
p.y =int( getmaxy()/2 + x*cos(RADS*45));
}
if(chieu==2)
{
p.x =int ( getmaxx()/2+y-x*cos(RADS*45)-y);
p.y =int ( getmaxy()/2-z+x*cos(RADS*45));
}
if(chieu == 3)
{
p.x =int( getmaxx()/2+y-x*cos(RADS*45)+x*sin(RADS*45));
p.y =int( getmaxy()/2-z);
}
return(p);
}
point quay(int &x, int &y, int &z, int goc , int chieu)
{
point p;
if(chieu==1)
{
p.x = x*cos(RADS*goc) + z*sin(RADS*goc);
p.z = -x*sin(RADS*goc) + z * cos(RADS*goc);
p.y = y;
}
if(chieu==2)
{
p.y = y*cos(RADS*goc) - z*sin(RADS*goc);
Ph lc 1
155
p.z = y*sin(RADS*goc) + z * cos(RADS*goc);
p.x =x;
}
if(chieu==3)
{
p.x = x*cos(RADS*goc)-y*sin(RADS*goc);
p.y = x*sin(RADS*goc)+y*cos(RADS*goc);
p.z = z;
}
return p;
}
void chieumat(point k[],int t, int m )
{
int i,j=0;
int n[4][4];
for(i = 0 ; i<4 ; i++)
for(j = 0 ; j<4 ; j++)
{
n[i][j]=1;
n[j][i]=1;
}
for(i = 0 ; i< 4 ; i++)
{
k[i] = hinhchieu(k[i].x,k[i].y,k[i].z,t);
}
for( i = 0 ; i< 4 ; i++)
for( j = 0 ; j< 4 ; j++)
{
if(i!=j&&n[i][j]==1&&n[j][i]==1)
{
Bresenham_Line(k[i].x,k[i].y,k[j].x,k[j].y,m);
n[i][j]=0;
n[j][i]=0;
}
}
}
void main()
{
clrscr();
point b[4],c[4],l[4];
int j=0;
int goc[2]={45,35};
int driver = DETECT, mode;
initgraph(&driver,&mode,"c:\\tc\\bgi");
Dothi();
for(int i = 0; i < 4; i ++)
b[i] = Diem3d(a[i].x,a[i].y,a[i].z);
for( i = 1; i < 4; i ++ )
{
Bresenham_Line(b[j].x,b[j].y,b[i].x,b[i].y,10);
Ph lc 1
156
}
Bresenham_Line(b[1].x,b[1].y,b[2].x,b[2].y,10);
Bresenham_Line(b[1].x,b[1].y,b[3].x,b[3].y,10);
Bresenham_Line(b[2].x,b[2].y,b[3].x,b[3].y,10);
settextjustify(LEFT_TEXT,RIGHT_TEXT);
printf("\nQuay quanh truc : oy goc 45");
printf("\nQuay quanh truc : ox goc 35.5");
for( i = 0 ; i< 4 ; i++)
{
c[i] = quay(a[i].x , a[i].y , a[i].z , goc[1] ,1);
}
for(i = 0 ; i< 4 ; i++)
{
c[i] = quay(c[i].x,c[i].y,c[i].z,goc[2],2);
}
for(i = 0; i< 4; i ++)
l[i] = c[i];
for( i = 0; i < 4; i ++)
c[i] = Diem3d(c[i].x,c[i].y,c[i].z);
outtextxy(10,110,"Chon mat chieu: ");
outtextxy(10,120,"xoy: Bam so 1.");
outtextxy(10,130,"xoz: Bam so 2.");
outtextxy(10,140,"yoz: Bam so 3.");
outtextxy(10,150,"Bam so 4 de ket thuc");
char m;
do{
m = getch();
for(i = 0;i < 4; i ++)
c[i] = l[i];
switch (m)
{
case '1' :{
chieumat(c,1,5);
break;
}
case '2' :{
chieumat(c,2,7);
break;
}
case '3' :
{
chieumat(c,3,9) ;
break;
}
}
}while( m !='4');
closegraph();
}
Bài 2: xén tỉa
#include <conio.h>
Ph lc 1
157
#include <graphics.h>
#include <math.h>
#include <stdlib.h>
#define ROUND(a) ((double)(a+0.5)
#define TRUE 1
#define FALSE 0
int cliptest(double p, double q, double *u1, double *u2)
{
double r;
int retVal = TRUE;
if (p < 0.0)
{
r = q / p;
if (r > *u2)
retVal = FALSE;
else
if (r > *u1)
*u1 = r;
}
else
if ( p > 0.0)
{
r = q / p;
if (r < *u1)
retVal = FALSE;
else
if (r < *u2)
*u2 = r;
}
else
{
if (q < 0.0)
retVal = FALSE;
}
return (retVal);
}
void clipline(double x1, double y1, double x2, double y2,
double xmin, double ymin, double xmax, double ymax)
{
double u1 = 0.0, u2 = 1.0, dx, dy;
double oldx1, oldy1, oldx2, oldy2;
oldx1 = x1;
oldy1 = y1;
oldx2 = x2;
oldy2 = y2;
dx = x2 - x1;
if (cliptest(-dx, x1 - xmin, &u1, &u2))
if (cliptest(dx, xmax-x1, &u1, &u2))
{
dy = y2 - y1;
Ph lc 1
158
if (cliptest(-dy, y1 - ymin, &u1, &u2))
if (cliptest(dy, ymax - y1, &u1, &u2))
{
if (u2 < 1.0)
{
x2 = x1 + u2 * dx;
y2 = y1 + u2 * dy;
}
if (u1 > 0.0)
{
x1 += u1 * dx;
y1 += u1 * dy;
}
setcolor(RED);
line(oldx1, oldy1, x1, y1);
line(x2, y2, oldx2, oldy2);
setcolor(YELLOW);
line(x1, y1, x2, y2);
}
}
}
void main()
{
int gr_drive = DETECT, gr_mode;
char c;
double x1, y1, x2, y2;
initgraph(&gr_drive, &gr_mode, "");
rectangle(100,50, getmaxx()-100, getmaxy()-50);
randomize();
outtextxy(100, getmaxy()-10, "Nhan phim bat ky de sinh duong khac; ESC de thoat");
do {
x1 = random(getmaxx() / 2);
y1 = random(getmaxy());
x2 = getmaxx()/2 + random(getmaxx() / 2);
y2 = random(getmaxy());
clipline(x1, y1, x2, y2, 100, 50, getmaxx()-100, getmaxy()-50);
c = getch();
} while (c != 27);
closegraph();
}
Bài 3: Phép chiếu
#include<stdio.h>
#include<dos.h>
#include<conio.h>
#include<graphics.h>
#include<stdlib.h>
#include<math.h>
#include<alloc.h>
#define RADS 0.017453293
struct point{
Ph lc 1
159
int x,y,z;
}
a[8]=
{
{30,100,50},
{30,230,50},
{30,230,90},
{30,100,90},
{120,100,50},
{120,230,50},
{120,230,90},
{120,100,90}
};
int n = 3,*d;
int noi[20][20];
void Dothi()
{
line (getmaxx()/2,getmaxy()/2,getmaxx()-10,getmaxy()/2);
line (getmaxx()/2,10,getmaxx()/2,getmaxy()/2);
line (getmaxx()/2,getmaxy()/2,getmaxx()/2-170,getmaxy()/2+170);
line (getmaxx()/2-170,getmaxy()/2+170,getmaxx()/2-170,getmaxy()/2+166);
line (getmaxx()/2-170,getmaxy()/2+170,getmaxx()/2-163,getmaxy()/2+167);
settextjustify(CENTER_TEXT,CENTER_TEXT);
outtextxy(getmaxx()-9,getmaxy()/2+1,"0");
outtextxy(getmaxx()-9,getmaxy()/2+10,"y");
outtextxy(getmaxx()/2,10,"-");
outtextxy(getmaxx()/2 - 10,10,"z");
outtextxy(getmaxx()/2-155,getmaxy()/2+170,"x");
}
point Diem3d(int &x, int &y, int &z)
{
point p;
p.x = int(getmaxx()/2+ y - x*cos(RADS*45));
p.y = int(getmaxy()/2 - z + x*cos(RADS*45));
return p;
}
point chance(int &x , int &y , int &z)
{
point p;
if(x>=0&&y>=0&&z>=0)
{
p.x = getmaxx()/2+y - x*cos(RADS*45);
p.y = getmaxy()/2-z + x*cos(RADS*45);
}
if(y>=0&&x<0&&z>=0)
{
p.x = y+getmaxx()/2-x*cos(RADS*45);
p.y = getmaxy()/2+z-x*cos(RADS*45);
}
Ph lc 1
160
if(x>=0&&y<0&&z>=0)
{
p.x = getmaxx()/2+y-x*cos(RADS*45);
p.y = getmaxy()/2-(z-x*cos(RADS*45));
}
if(x>=0&&y>=0&&z<0)
{
p.x = getmaxx()/2+(sqrt(pow(x,2)+pow(y,2)))*cos(RADS*45);
p.y = getmaxy()/2+(sqrt(pow(x,2)+pow(y,2)))*cos(RADS*45)-z;
}
if(y>=0&&x<0&&z<0)
{
p.x = getmaxx()/2+y-x*cos(RADS*45);
p.y = getmaxy()/2+(-z-x*cos(RADS*45));
}
return(p);
}
point hinhchieu(int &x, int &y , int &z , int chieu)
{
point p;
if(chieu==1)
{
p.x =int( getmaxx()/2+y - x*cos(RADS*45));
p.y =int( getmaxy()/2+x*cos(RADS*45));
}
if(chieu==2)
{
p.x =int ( getmaxx()/2+y-x*cos(RADS*45)-y);
p.y =int ( getmaxy()/2-z+x*cos(RADS*45));
}
if(chieu == 3)
{
p.x =int( getmaxx()/2+y-x*cos(RADS*45)+x*sin(RADS*45));
p.y =int( getmaxy()/2-z);
}
return(p);
}
point quay(int &x, int &y, int &z, int goc , int chieu)
{
point p;
if(chieu==1)
{
p.x = x*cos(RADS*goc) + z*sin(RADS*goc);
p.z = -x*sin(RADS*goc) + z * cos(RADS*goc);
p.y = y;
}
if(chieu==2)
{
p.y = y*cos(RADS*goc) - z*sin(RADS*goc);
p.z = y*sin(RADS*goc) + z * cos(RADS*goc);
Ph lc 1
161
p.x =x;
}
if(chieu==3)
{
p.x = x*cos(RADS*goc)-y*sin(RADS*goc);
p.y = x*sin(RADS*goc)+y*cos(RADS*goc);
p.z = z;
}
return p;
}
void chieumat(point k[],int t, int &m )
{
int i,j;
for(i = 0 ; i< 8 ; i++)
k[i] = hinhchieu(k[i].x,k[i].y,k[i].z,t);
for( i = 0 ; i< 8 ; i++)
for( j = 0 ; j< 8 ; j++)
{
if(noi[i][j]==1&&noi[j][i]==1)
{
Bresenham_Line(k[i].x,k[i].y,k[j].x,k[j].y,m);
}
}
noi[0][3]=1,noi[3][0]=1;
noi[4][7]=1,noi[7][4]=1;
noi[3][7]=1,noi[7][3]=1;
}
void main()
{
clrscr();
d = &n;
point b[8],g[3][8],c[8],l[8];
int t, goc ;
int driver = DETECT, mode;
initgraph(&driver,&mode,"c:\\tc\\bgi");
Dothi();
for(int i = 0; i < 8; i ++)
b[i] = Diem3d(a[i].x,a[i].y,a[i].z);
for( i = 0; i < 3; i ++ )
{
line(b[i].x,b[i].y,b[i + 4].x,b[i + 4].y);
line(b[i].x,b[i].y,b[i+1].x,b[i+1].y);
line(b[i+4].x,b[i+4].y,b[i+5].x,b[i+5].y);
noi[i][i+4]=1 , noi[i+4][i] =1;
noi[i][i+1] = 1, noi[i+1][i]=1;
noi[i+4][i+5]=1, noi[i+5][i+4]=1;
}
noi[0][3]=1,noi[3][0]=1;
noi[4][7]=1,noi[7][4]=1;
noi[3][7]=1,noi[7][3]=1;
Ph lc 1
162
line(b[0].x,b[0].y,b[3].x,b[3].y);
line(b[4].x,b[4].y,b[7].x,b[7].y);
line(b[3].x,b[3].y,b[7].x,b[7].y);
settextjustify(LEFT_TEXT,RIGHT_TEXT);
printf("\nQuay quanh truc :");
printf("\ny.Bam so 1");
printf("\nx.Bam so 2.");
printf("\nz.Bam so 3.");
scanf("%d",&t);
printf("\nQuay goc bao nhieu do:");
scanf("%d",&goc);
for( i = 0 ; i<= 7 ; i++)
{
c[i] = quay(a[i].x , a[i].y , a[i].z , goc ,t);
l[i] = c[i];
}
for( i = 0; i < 8; i ++)
c[i] = Diem3d(c[i].x,c[i].y,c[i].z);
for( i = 0; i < 3; i ++ )
{
line(c[i].x,c[i].y,c[i + 4].x,c[i + 4].y);
line(c[i].x,c[i].y,c[i+1].x,c[i+1].y);
line(c[i+4].x,c[i+4].y,c[i+5].x,c[i+5].y);
}
line(c[0].x,c[0].y,c[3].x,c[3].y);
line(c[4].x,c[4].y,c[7].x,c[7].y);
line(c[3].x,c[3].y,c[7].x,c[7].y);
outtextxy(10,410,"Chon mat chieu: ");
outtextxy(10,420,"xoy: Bam so 1.");
outtextxy(10,430,"xoz: Bam so 2.");
outtextxy(10,440,"yoz: Bam so 3.");
outtextxy(10,450,"Bam so 4 de ket thuc");
char m;
do{
m = getch();
for(i = 0;i < 8; i ++)
c[i]= l[i];
switch (m)
{
case '1' :{
chieumat(c,1,*(d));
break;
}
case '2' :{
chieumat(c,2,*(d));
break;
}
case '3' :
{
chieumat(c,3,*(d)) ;

break;

}
}
}while( m !='4');
closegraph();

}