/*****************************************************/
/* Author: Antonio Medina and Fawzan Ghulam */
/* Date: 10-2-04 */
/* EE1E2 FINAL PROJECT */
/* DRAWING PACKAGE */
/*****************************************************/
#include <stdio.h>
#include <string.h>
#include <malloc.h>
#include <math.h>
#define PI 3.14
struct drawing
{
int width;
int height;
char** data;
}A;
struct node
{
char name[6];
int ID_no;
int x1;
int x2;
int y1;
int y2;
int centrex;
int centrey;
int radius;
struct node* next;
};
struct node* mknode(char name[6], int ID_no,int x1,int x2,int y1,int y2,int radius,int centrex,int centrey)
{
struct node* np;
np = (struct node*)malloc(sizeof(struct node));
if (np)
{
strcpy(np->name,name);
np->ID_no=ID_no;
np->x1=x1;
np->x2=x2;
np->y1=y1;
np->y2=y2;
np->centrex=centrex;
np->centrey=centrey;
np->radius=radius;
np->next=NULL;
}
return np;
}
struct node* append_node(struct node** head, struct node* np)
{
struct node* n;
if(*head==NULL)
*head=np;
else
{
for (n=*head; n->next!=NULL; n=n->next);
n->next=np;
}
return np;
}
void display_list(struct node* head)
{
struct node* n;
for (n=head; n!=NULL; n=n->next)
{
if (strcmp(n->name,"rect")==0)
printf("%d: %s from %d %d to %d %d\n", n->ID_no, n->name, n->x1, n->y1, n->x2, n->y2);
else if (strcmp(n->name,"circle")==0)
printf("%d: %s, centre %d %d and radius %d\n", n->ID_no, n->name, n->centrex, n->centrey, n->radius);
else if (strcmp(n->name,"line")==0)
printf("%d: %s from %d %d to %d %d\n", n->ID_no, n->name, n->x1, n->y1, n->x2, n->y2);
}
}
void commands (void)
{
printf("*********************\n");
printf("* POSSIBLE COMMANDS *\n");
printf("*********************\n");
printf(" -----------------------------------------------\n");
printf("| - create (width) (height) |\n");
printf("| - r |\n");
printf("| - clear |\n");
printf("| - invert |\n");
printf("| - line (from) (to) |\n");
printf("| - rect (corner1, corner2) (corner3, corner4) |\n");
printf("| - circle (centre) (radius) |\n");
printf("| - fill (x) (y) |\n");
printf("| - list |\n");
printf("| - delete (object_number) |\n");
printf("| - exit |\n");
printf(" -----------------------------------------------\n");
}
void create(struct drawing *p1)
{
int width, height;
p1->data=(char**)(malloc(p1->width*sizeof(char*)));
for(width=0; width<p1->width; width++)
p1->data[width]=(char*)(malloc(p1->height*sizeof(char)));
for(width=0; width<p1->width; width++)
for(height=0; height<p1->height; height++)
p1->data[width][height]='.';
}
void invert(struct drawing *p1)
{
int width, height;
for(width=0; width<p1->width; width++)
for(height=0; height<p1->height; height++)
if(p1->data[width][height]=='*')
p1->data[width][height]='.';
else if(p1->data[width][height]=='.')
p1->data[width][height]='*';
}
void clear(struct drawing *p1)
{
int width, height;
for(width=0; width<p1->width; width++)
for(height=0; height<p1->height; height++)
p1->data[width][height]='.';
}
void refresh(struct drawing *p1)
{
int width, height;
for(height=p1->height-1; height>=0; height--)
{
for(width=0; width<p1->width; width++)
printf("%c", p1->data[width][height]);
printf("\n");
}
}
void line(struct drawing *p1, int x1, int x2, int y1, int y2, int del)
{
int dx, dy, i,j;
if((x1<0)||(x2<0)||(y1<0)||(y2<0))
printf("Error. You can't draw a negative line\n");
else if((x1>p1->width)||(x2>p1->width)||(y1>p1->height)||(y2>p1->height))
printf("Error. Your line has excedeed the image limits\n");
else if ((y1<x1)||(y2<x2))
printf("Error. You can't draw that shape.\n");
else
{
dx=x2-x1;
dy=y2-y1;
if(dx>p1->width||dy>p1->height)
printf("Your dimensions are too large for the grid");
else
{
if(dx>dy)
{
if(dx>0)
{
for(i=0; i<dx; i++)
{
j=(((i*dy)/dx)+0.5);
p1->data[x1+i][y1+j]='*';
}
}
else
{
for(i=0; i<dx; i--)
{
j=(((i*dy)/dx)+0.5);
p1->data[x1+i][y1+j]='*';
}
}
}
else
{
if(dy>0)
{
for(j=0; j<dy; j++)
{
i=(((j*dx)/dy)+0.5);
p1->data[x1+i][y1+j]='*';
}
}
else
{
for(j=0; j<dy; j--)
{
i=(((j*dx)/dy)+0.5);
p1->data[x1+i][y1+j]='*';
}
}
}
}
}
}
void circle(struct drawing *p1, int x1, int y1, int r, int del)
{
int i, j;
float deg, theta;
if((x1<0)||(y1<0))
printf("Error. You can't draw a negative circle\n");
else if((x1>p1->width)||(y1>p1->height))
printf("Error. Your circle has excedeed the image limits\n");
else
{
for(deg=0; deg<=360; deg=deg+5)
{
theta=((deg*PI)/180);
i=x1+r*cos(theta)+0.5;
j=y1+r*sin(theta)+0.5;
p1->data[i][j]='*';
}
}
}
void rect(struct drawing *p1, int x1, int x2, int y1, int y2, int del)
{
int dx, dy, i;
if((x1<0)||(x2<0)||(y1<0)||(y2<0))
printf("Error. You can't draw a negative rectangle\n");
else if((x1>p1->width)||(x2>p1->width)||(y1>p1->height)||(y2>p1->height))
printf("Error. Your rect has excedeed the image limits\n");
else if ((y1<x1)||(y2<x2))
printf("Error. You can't draw that shape.\n");
else
{
dx=x2-x1;
dy=y2-y1;
if(dx>p1->height||dy>p1->width)
printf("Your dimensions are too large for the grid");
else
{
if((dy>0)&&(dx>0))
{
for (i=0; i<dx; i++)
p1->data[x1+i][y1]='*';
for (i=0; i<dy; i++)
p1->data[x1][y1+i]='*';
for (i=dx;i>=0; i--)
p1->data[x2-i][y2]='*';
for (i=dy;i>=0; i--)
p1->data[x2][y2-i]='*';
}
else if((dy<0)&&(dx<0))
{
for (i=dx; i<=0; i++)
p1->data[x1+i][y1]='*';
for (i=dy; i<=0; i++)
p1->data[x1][y1+i]='*';
for (i=dx;i<=0; i++)
p1->data[x2-i][y2]='*';
for (i=dy;i<=0; i++)
p1->data[x2][y2-i]='*';
}
else if(dy>0&&dx<0)
{
for (i=dx; i<=0; i++)
p1->data[x1+i][y1]='*';
for (i=0; i<dy; i++)
p1->data[x1][y1+i]='*';
for (i=dx;i<=0; i++)
p1->data[x2-i][y2]='*';
for (i=dy;i>=0; i--)
p1->data[x2][y2-i]='*';
}
else if((dy<0)&&(dx>0))
{
for (i=0; i<=dx; i++)
p1->data[x1+i][y1]='*';
for (i=dy; i<=0; i++)
p1->data[x1][y1+i]='*';
for (i=dx;i>=0; i--)
p1->data[x2-i][y2]='*';
for (i=dy;i<=0; i++)
p1->data[x2][y2-i]='*';
}
}
}
}
void fill(int x, int y, struct drawing *p1)
{
p1->data[x][y]='*';
if((x+1>=0)&&(x+1<p1->width))
if((y>=0)&&(y<p1->height))
if(p1->data[x+1][y]=='.')
fill(x+1,y, p1);
if((x-1>=0)&&(x-1<p1->width))
if((y>=0)&&(y<p1->height))
if(p1->data[x-1][y]=='.')
fill(x-1,y, p1);
if((x>=0)&&(x<p1->width))
if((y+1>=0)&&(y+1<p1->height))
if(p1->data[x][y+1]=='.')
fill(x,y+1, p1);
if((x>=0)&&(x<p1->width))
if((y-1>=0)&&(y-1<p1->height))
if(p1->data[x][y-1]=='.')
fill(x,y-1, p1);
}
int delete_object(struct node** head, int ID_no, struct drawing *p1)
{
struct node* n;
struct node* np;
int del=1;
if (*head==NULL)
return 0;
else if (ID_no==(*head)->ID_no)
{
np=(*head);
if(strcmp(np->name,"circle")==0)
circle(&A,np->centrex,np->centrey,np->radius,del);
}
if(strcmp(np->name,"line")==0)
line(&A,np->x1,np->y1,np->x2,np->y2,del);
if(strcmp(np->name,"rect")==0)
{
rect(&A,np->x1,np->y1,np->x2,np->y2,del);
*head=(*head)->next;
free(np);
return 1;
}
else
{
for(n=*head; (n->ID_no!=ID_no)&&(n->next!=NULL); n=n->next)
np=n;
if(n->ID_no==ID_no)
{
if(strcmp(n->name,"circle")==0){
circle(&A,n->centrex,n->centrey,n->radius,del);
}
else if(strcmp(n->name,"line")==0)
{
line(&A,n->x1,n->y1,n->x2,n->y2,del);
}
else if(strcmp(n->name,"rect")==0)
{
rect(&A, n->x1, n->y1,n->x2,n->y2,del);
}
np->next=n->next;
free(n);
return 1;
}
else
return 0;
}
}
int main (void)
{
char a[6];
struct drawing A;
struct node *n;
struct node *head=NULL;
int flag=0, i ,j, k=1, x1=0, x2=0, y1=0, y2=0, r, x=0, y=0, del=0, ID_no=0;
printf("DRAWING PACKAGE FOR MS-DOS 1.0\n");
printf("------------------------------\n");
printf("\n");
commands();
printf("Enter your command:\n");
while(strcmp(a, "exit")!=0)
{
scanf("%s", a);
if(strcmp(a, "create")==0)
{
if(flag==1)
printf("Error. You can't create more than one image per session.\n");
else
{
printf("Enter width:");
scanf("%d", &A.width);
printf("Enter height:");
scanf("%d", &A.height);
create(&A);
flag++;
}
}
else if(strcmp(a, "r")==0)
refresh(&A);
else if(strcmp(a, "invert")==0)
invert(&A);
else if(strcmp(a, "exit")==0)
{
printf("\n");
printf("Thanks for using this program\n");
printf("-----------------------------\n");
return 0;
}
else if(strcmp(a, "clear")==0)
clear(&A);
else if(strcmp(a, "fill")==0)
{
printf("Enter starting point:");
scanf("%d %d", &i, &j);
fill(i, j, &A);
}
else if(strcmp(a, "list")==0)
display_list(head);
else if(strcmp(a, "delete")==0)
{
printf("Enter ID:");
scanf("%d", &ID_no);
if(delete_object(&head,ID_no,&A))
printf("Object no.%d successfully deleted\n", ID_no);
}
else if((strcmp(a, "line"))||(strcmp(a, "circle"))||(strcmp(a, "rect"))==0)
{
if(strcmp(a, "line")==0)
{
printf("Insert point 1\n");
scanf("%d %d", &x1,&y1);
printf("Insert point 2\n");
scanf("%d %d", &x2,&y2);
line(&A, x1, x2, y1, y2, del);
}
else if(strcmp(a, "circle")==0)
{
printf("Enter Coordinates:");
scanf("%d %d", &x1, &y1);
printf("Enter Radius:");
scanf("%d", &r);
circle(&A, x1, y1, r, del);
}
else if(strcmp(a, "rect")==0)
{
printf("Enter x1, y1:");
scanf("%d %d", &x1, &y1);
printf("Enter x2, y2:");
scanf("%d %d", &x2, &y2);
rect(&A, x1, x2, y1, y2, del);
}
n=mknode(a, k, x1, x2, y1, y2, r, x, y);
append_node(&head, n);
k++;
}
else
printf("Error. That is not a possible command.\n");
}
return 0;
}