ТЕХНИЧЕСКИЕ НАУКИ
ИСПОЛЬЗОВАНИЕ МЕТОДА ПРОСТОГО ДВУМЕРНОГО ОТСЕЧЕНИЯ ДЛЯ _ОТСЕЧЕНИЯ ЗАДАННОЙ ФИГУРЫ ПРЯМОУГОЛЬНЫМ ОКНОМ_
Ананьева Марина Алексеевна
старший преподаватель Московский технологический университет
МИРЭА г. Москва
USE OF METHOD SIMPLE TWO-DIMENSIONAL CLIPPING FOR CLIPPING SET FIGURE
BOXED WINDOW
Ananieva Marina Alekseevna
older teacher of Moskow technological university MIREA, MOSCOW
АННОТАЦИЯ
Отсечение применяется в компьютерной графике в алгоритмах удаления невидимых линий и поверхностей, при построении теней, а также при формировании фактуры. Рассматривается фигура с отсекающим прямоугольным окном, параллельным осям координат экрана. Окно задаётся левым(х1), правым(хг), нижним(уп), верхним(уу) двумерными окнами. Целью алгоритма отсечения является определение отрезков или их частей, которые лежат внутри отсекающего окна. Остальные части отбрасываются. Для отсечения используется простой алгоритм двумерного отсечения [1].
ABSTRACT
The clipping use in computer graphics in algorithm deletion of hidden line and surfaces, by acquisition shades, is also at generation of facture. Examine figure with clipping boxed window, the parallel axis of coordinate screen. The windows set left (xl), right (xr), bottom (yn), top(yv) two-dimensional windows. The end of algorithm clipping appear declaration runs or them parts, that lay in clipping windows. The rest part cast. For clipping use the simple algorithm two-dimensional clipping .
Ключевые слова: отсечение,линия.
Keywords: clipping, line.
//программа написана на языке C++Builder 6
#include <vcl.h>
#pragma hdrstop
#include<math.h>
#include<string .h>
#define C_M Form1->Canvas->MoveTo
#define C_L Form1->Canvas->LineTo
#define C_P Form1->Canvas->Pixels
#define C_P_C Form1->Canvas->Pen->Color
#define C_P_W Form1->Canvas->Pen->Width
#define C_B_C Form1->Canvas->Brush->Color
#define C_T Form1->Canvas->TextOutA
#define R_B RGB(200,200,200)
#define cW clWhite
#define cB clBlack
#define cM clMaroon
#define R_G RGB(0,121,0)
#include "Article19.h"
#pragma package(smart_init)
#pragma resource "*.dfm"
TForm1 *Form1;
int mx=30,my=30; struct Point {int x;
int y;};
//--------------------------------------------------------
_fastcall TForm1::TForm1(TComponent* Owner)
: TForm(Owner)
{ }
//--------------------------------------------------------
void_fastcall TForm1::ShowGrid()
{int x,y;
C_P_C=(TColor)R_B;
//горизонтальные линии сетки for (y=0 ;y<=17* my;y+=my) {C_M(0,y); C_L(20*mx,y); } //вертикальные линии сетки for (x=0 ;x<=20*mx;x+=mx) {C_M(x,0); C_L(x,17*my); }}
//--------------------------------------------------------
int_fastcall TForm1::Sign(int n)
{if (n>0) return 1;
else if (n==0)return 0; else if (n<0) return -1;}
//........................................................
void_fastcall TForm1::BrezenshemLine(int x1, int
y1, int x2, int y2, int color) {int dx,dy,sx,sy,flag,e,x,y,buf; //инициализация переменных dx=abs(x1-x2); dy=abs(y2-y1); sx=Sign(x2-x1); sy=Sign(y2-y1); x=x1; y=y1;
// обмен значений dx и dy в зависимости от углового
// коэффициэнта наклона отрезка flag=0; if (dy>dx)
{ buf=dx; dx=dy; dy=buf; flag=1;} // инициализация ошибки с поправкой на половину пиксела e=2*dy-dx; // основной цикл for(int i=0;i<=dx;++i) {C_P[x] [y]=(TColor)color; if (e>=0) { if (flag==1)
x+=sx; else y+=sy; e-=2*dx;} if (flag==1)
y+=sy; else x+=sx; e+=2*dy;}} //--------------------------------------------------------
void_fastcall TForm1::Otsechenie(int x1, int y1,
int x2, int y2,
int xl, int yn, int xr, int yv, int color) {int
T1[4] ,T2[4],flag,s1,s2,pr,i,x,y,P1X,P1Y,P2X,P2Y; float k;
//для первого конца:Р1 if (x1 <xl) T1[3]=1;else T1[2]=1;else T1[2]=0; if (y 1<yn) T1[1]=1;else T1[0]=1;else T1[0]=0; //для второго конца:Р2 if (x2<xl) T2[3]=1;else T2[2]=1;else T2[2]=0; if (y2<yn) T2[1]=1;else T2[0]=1;else T2[0]=0; //инициализация признака видимости и видимых //концевых точек
flag=0; P1X=x1;P1Y=y1;P2X=x2;P2Y=y2;
//проверка полной видимости отрезка
s1=0;s2=0;
for(i=0;i<4;i++)
{s1+=T1 [i] ;s2+=T2[i];}
if (s1==0 && s2==0) goto M1;
//проверка случая тривиальной невидимости
pr=0;
for(i=0;i<4;i++) pr+=(int)((T1[i]+T2[i])/2.); if(pr!=0) {flag==-1;goto M2;} if (x1==x2) k=1;else k=(float)(y2-y1)/(x2-x1); //горизонтальные линии if (x 1<xl && x2>xr) if (y1==y2)
{P1X=xl; P1Y=y1; P2X=xr; P2Y=y2; goto M1;} //вертикальные линии if (y1<yn && y2>yv) if (x1==x2)
{P1X=x1; P1Y=yn; P2X=x2; P2Y=yv; goto M1;} //пересечение с верхним краем
if (y2>yv && x1==x2) {y=y2+ (yv-y2);
P1X=x1; P1Y=y1; P2X=x2; P2Y=y; goto M1;}
//наклонные линии
//проверка пересечения с нижним краем if (y1<yn)
{x=(int)(x1+1./k*(yn-y1)); P1X=x; P1Y=yn; P2X=x2; P2Y=y2; goto M1;} //пересечение с верхним краем if (y2>yv)
{x=(int)(x1+1./k*(yv-y1)); P1X=xl; P1Y=y1; P2X=x; P2Y=yv; goto M1;} //пересечение с левым краем if (x2<xl)
{y=(int)(k*(xl-x2)+y2); P1X=x1; P1Y=y1; P2X=xl; P2Y=y; goto M1;} //пересечение с правым краем if (x2>xr)
{y=y2-(int)(k*(x2-xr)); P1X=x1; P1Y=y1; P2X=xr; P2Y=y;} M1:;
BrezenshemLine(P1X,P1Y,P2X,P2Y,color); M2:;}
//--------------------------------------------------------
void _fastcall TForm1::FormPaint(TObject
*Sender)
{Color=(TColor)cW; int y;
struct Point P1[]={4*mx,3*my, 4*mx,14*my, 16*mx,3*my,
8*mx,3*my,12*mx,3*my,8*mx,7*my,10*mx,7*my,
7*mx,9*my,10*mx,9*my,6*mx,11*my,9.5*mx,11* my,
10.5*mx,11*my,4*mx,5*my,4*mx,12.5*my, 6*mx,3*my,
14*mx,3*my,6*mx,5*my,6*mx,12.5*my,14*mx,5* my};
struct Point P2[]={
4*mx,14*my,16*mx,3*my,16*mx,14*my,
12*mx,7*my,8*mx,7*my,7*mx,9*my,13*mx,9*my,
T1[3]=0;if (x1>xr)
T1[1]=0;if (y1>yv)
T2[3]=0;if (x2>xr)
T2[1]=0;if (y2>yv)
4*mx,12*my,16*mx,12*my,14*mx,11*my, 9.5*mx,14*my,
10.5*mx,14*my,16*mx,5*my,16*mx,12.5*my,6*m x,14*my,
14*mx,14*my,14*mx,5*my,14*mx,12.5*my,6*mx,
12.5*my };
ShowGrid();
if (CheckBox1->Checked==false)
{//квадрат Brezenshem-
Line(P 1[0] .x,P1[0].y,P2[0] .x,P2[0] .y,cB);//ad Brezenshem-
Line(P 1[0] .x,P1[0].y,P2[1] .x,P2[1 ] .y,cB);//ab Brezenshem-
Line(P 1[1].x,P1[1].y,P2[2] .x,P2[2] .y,cB);//dc Brezenshem-
Line(P 1[2] .x,P1 [2] .y,P2[2] .x,P2[2] .y,cB);//bc
C_T(4*mx,2.1*my,"a");C_T(16*mx,2.1*my,"b");
C_T(4*mx,14.2*my,"d");C_T(16*mx,14.2*my,"c");
//ёлка //1
Brezenshem-
Line(P 1[3] .x,P1 [3] .y,P2[3] .x,P2[3] .y,cB);//xw Brezenshem-
Line(P 1[4] .x,P1 [4] .y,P2[4] .x,P2[4] .y,cB);//yz Brezenshem-
Line(P 1[5] .x,P1 [5] .y,P2[3] .x,P2[3] .y,cB);//zw
C_T(8*mx,2.1*my,"x");C_T(12*mx,2.1*my,"y");
C_T(8*mx,7.1*my,"z");C_T(12*mx,7.1*my,"w");
//2
Brezenshem-
Line(P 1[6] .x,P1 [6] .y,P2[5] .x,P2[5] .y,cB);//uv Brezenshem-
Line(P 1[6] .x,P1[6].y,P2[6] .x,P2[6] .y,cB);//up Brezenshem-
Line(P 1[7] .x,P1[7].y,P2[6] .x,P2[6] .y,cB);//vp
C_T(10.2*mx,6.2*my,"u");C_T(7*mx,9.1*my,"v");
C_T(13*mx,9.1*my,"p");
//3
Brezenshem-
Line(P1[8] .x,P1 [8] .y,P2[7] .x,P2[7] .y,cB);//qs Brezenshem-
Line(P 1[8] .x,P1 [8] .y,P2[8] .x,P2[8] .y,cB);//qf Brezenshem-
Line(P 1[9] .x,P1[9].y,P2[9] .x,P2[9] .y,cB);//ij C_T(10.2*mx,8.2*my,"q");C_T(3.5*mx,11.2*my,"s ");
C_T(16.2*mx,11.2*my,"f');C_T(6.1*mx,11.2*my," i");
C_T(14.2*mx,10.1*my,"j");
//ствол
Brezenshem-
Line(P 1[10].x,P1[10] .y,P2[ 10] .x,P2[ 10] .y,cB);//gr Brezenshem-
Line(P 1[ 11].x,P1[11] .y,P2[11].x,P2[ 11] .y,cB);//ht
C_T(9.1*mx,11.2*my,"g");C_T(9.1*mx,14.2*my,"r ");
C_T(10.7*mx,11.2*my,"h");C_T(10.7*mx,14.2*my ,"t");
//горизонтальные линии Brezenshem-
Line (P1[12].x,P1[12].y,P2[12].x,P2[12].y,cB);//kl Brezenshem-
Line(P 1[13] .x,P1[13] .y,P2[13] .x,P2[ 13] .y,cB);//mn C_T(3.5*mx,4.2*my,"k");C_T(16.2*mx,4.2*my,"l")
C_T(3.3*mx,12.1*my,"m");C_T(16.2*mx,12.1*my, "n");
//вертикальные линии Brezenshem-
Line (P1[14].x,P1[14].y,P2[14].x,P2[14].y,cB);//eo Brezenshem-
Line(P 1[15] .x,P1[15] .y,P2[15] .x,P2[ 15] .y,cB);//rrtt C_T(6*mx,2.1*my,"e");C_T(6*mx,14.2*my,"o");
C_T(14*mx,2.1*my,"rr");C_T(14*mx,14.2*my,"tt")
;}
else
{//окно, отсечение
//квадрат
Otseche-
nie(P 1[0].x,P1 [0] .y,P2[0] .x,P2[0] .y,P1[16].x,P1[16].
y,
P2[17].x,P2[17].y,R_G);//ad Otseche-
nie(P 1[0].x,P1 [0] .y,P2[1] .x,P2[1] .y,P1[16].x,P1[16].
y,
P2[17].x,P2[17].y,R_G);//ab Otseche-
nie(P 1[1].x,P1[1].y,P2[2] .x,P2[2].y,P1[16].x,P1[16].
y,
P2[17].x,P2[17].y,R_G);//dc Otseche-
nie(P 1[2] .x,P1 [2] .y,P2[2] .x,P2[2] .y,P1[16].x,P1[16].
y,
P2[17].x,P2[17].y,R_G);//ji
//ёлка //1
Otseche-
nie(P 1[3] .x,P1 [3] .y,P2[3] .x,P2[3] .y,P1[16] .x,P 1[16].
y,
P2[17].x,P2[ 17] y,R_G);//xw Otseche-
nie(P 1[4] .x,P1 [4] .y,P2[4] .x,P2[4] .y,P1[16].x,P1[16].
y,
P2[17].x,P2[17].y,R_G);//yz Otseche-
nie(P 1[5] .x,P1 [5] .y,P2[3] .x,P2[3] .y,P1[16] .x,P 1[16].
y,
P2[17].x,P2[17].y,R_G);//zw
//2
018есЬе-
п1е(Р 1[6] .х,Р1[6].у,Р2[6] .х,Р2[6] .у,Р1[16].х,Р1[16].
У,
Р2[17] .х,Р2[ 17] уД_0) ;//ир 018ееЬе-
п1е(Р 1[6] .х,Р1[6].у,Р2[5] .х,Р2[5] .у,Р1[16].х,Р1[16].
у,
Р2[17].х,Р2[17] уД_0) ;//иу 018ееЬе-
п1е(Р 1[7] .х,Р1[7].у,Р2[6] .х,Р2[6] .у,Р1[16].х,Р1[16].
у,
Р2[17].х,Р2[17] уД_0) ;//ур //3
018ееЬе-
п1е(Р1[8].х,Р1[8].у,Р2[8] .х,Р2[8] .у,Р1[16].х,Р1[16].
у,
Р2[17].х,Р2[17] уД_0) 018ееЬе-
п1е(Р1[8].х,Р1[8].у,Р2[7] .х,Р2[7] .у,Р1[16].х,Р1[16].
у,
Р2[17].х,Р2[17] уД_0) 018ееЬе-
п1е(Р 1[9] .х,Р1[9].у,Р2[9] .х,Р2[9] .у,Р1[16].х,Р1[16].
у,
Р2[17].х,Р2[17].уД_0);//у
//ствол
018ееЬе-
п1е(Р 1[10].х,Р1[10] .у,Р2[10] х,Р2 [ 10] .у,Р1[16].х,Р1 [16].у,
Р2[17] .х,Р2[ 17] .у,сМ);/^г 018ееЬе-
п1е(Р1[11] .х,Р1[11] .у,Р2[11].х,Р2[ 11].у,Р1[16] .х,Р1 [16].у,
Р2[17].х,Р2[17].у,сМ);//Ы
//горизонтальные линии 018ееЬе-
п1е(Р 1[12].х,Р1[12] .у,Р2[12] .х,Р2[ 12].у,Р1[16] .х,Р1 [16].у,
Р2[17].х,Р2[17].у,сМ);//к1 018есЬе-
п1е(Р 1[13] .х,Р1[13] .у,Р2[13].х,Р2[ 13] у,Р1[16] .х,Р1 [16].у,
Р2[17].х,Р2[17].у,сМ);//тп
//вертикальные линии 018есЬе-
п1е(Р 1[14].х,Р1[14] .у,Р2[14] .х,Р2[ 14].у,Р1[16] .х,Р1 [16].у,
Р2[17].х,Р2[17].у,сМ);//ео 018есЬе-
п1е(Р 1[15] .х,Р1[15] .у,Р2[15].х,Р2[ 15] у,Р1[16].х,Р1 [16].у,
Р2[17] .х,Р2[ 17] .у,сМ);//ггй }}
Отсечение 1 = \гт -вз-
а е X У гг Ь
\ /
к 1
/ и \
2 х w
X \
V \ р
]
э 1 9 И 1
т П
<1 о г 1 Н с
Рисунок 1. Заданная фигура
/ \
/ \
X
Рисунок 2. Фигура после отсечения
Список литературы:
1. Роджерс Д. Алгоритмические основы машинной графики. /Пер. с англ. С. А. Вичеса, Г. В. Олохтоновой и П. А. Монахова/ под редакцией Ю. М. Баяковского и В. А. Галактионова-М.: Мир, 1989.-512с.: ил.
2. Шикин Е.В., Боресков А.В. Компьютерная графика. Полигональные модели. - М.: ДИАЛОГ-МИФИ, 2005.-464с.: ил.
3. Ананьева М.А. Компьютерная графика. Лабораторный практикум (Учебное пособие) для бакалавров, обучающихся по направлению 231300, часть 1.-М.:МИРЭА, 2012.-184с.