На этом шаге мы рассмотрим реализацию алгоритма вывода эллипса.
Инкрементный алгоритм для эллипса подобен алгоритму для круга, но более сложный. Этот алгоритм приведен в [1].
void Ellipse (HDC hdc,int xc, int yc, int enx, int eny,BYTE red,BYTE gre,BYTE blu) { int x,y; double k; long a2,b2,dds,ddt,t,s,e,ca,cd,indx,dxt; int a,b; a=abs(enx-xc); b=abs(eny-yc); a2=(long)a*(long)a; b2=(long)b*(long)b; dds=4*a2; ddt=4*b2; dxt=(float)a2/sqrt(a2+b2); t=0; s=-4*a2*b; e=(-s/2)-2*b2-a2; ca=-6*b2; cd=ca-4*a2; x=xc; y=yc+b; SetPixel(hdc,x,y,0); SetPixel(hdc,x,2*yc-y,0); SetPixel(hdc,2*xc-x,2*yc-y,0); SetPixel(hdc,2*xc-x,y,0); for(indx=1;indx<=dxt;indx++) { x++; if(e>=0)e+=t+ca; else { y--; e+=t-s+cd; s+=dds; } t-=ddt; SetPixel(hdc,x,y,0); SetPixel(hdc,x,2*yc-y,0); SetPixel(hdc,2*xc-x,2*yc-y,0); SetPixel(hdc,2*xc-x,y,0); } dxt=abs(y-yc); e-=t/2+s/2+b2+a2; ca=-6*a2; cd=ca-4*b2; for(indx=1;indx<=dxt;indx++) { y--; if(e<=0) e+=-s+ca; else { x++; e+=-s+t+cd; t-=ddt; } s+=dds; SetPixel(hdc,x,y,0); SetPixel(hdc,x,2*yc-y,0); SetPixel(hdc,2*xc-x,2*yc-y,0); SetPixel(hdc,2*xc-x,y,0); } }
Результат работы приложения изображен на рисунке 1.
Рис.1. Результат работы приложения
В этом алгоритме использована симметрия эллипса по квадрантам (рисунок 2).
Рис.2. Вывод эллипса
Алгоритм состоит из двух циклов. Сначала от x = 0 до x = dxt, где
а потом цикл до точки x = a, y = 0.На следующем шаге мы рассмотрим алгоритм вывода кривой Безье.