chiark / gitweb /
rewrap parameters
[moebius.git] / graphics.cc
1 /*
2  * Graphics library
3  */
4
5 #include <iostream.h>
6
7 #include <string.h>
8 #include <stdio.h>
9 #include <stdlib.h>
10 #include <math.h>
11
12 #include "library.hh"
13 #include "graphics.hh"
14 #include "output.hh"
15
16 static int checkneededline(Onscreen a, Onscreen b) {
17   double xd= a.x - b.x;
18   double yd= a.y - b.y;
19   int n= (int)ceil(sqrt(xd*xd+yd*yd)*100.0);
20   return n>0 ? n : 1;
21 }
22
23 void Cell::display(Output& o) {
24   int nn[4];
25   int totalnn= 0;
26   int i;
27   for (i=0; i<4; i++) {
28     nn[i]= checkneededline(p[i],p[(i+1)&3]);
29     totalnn+= nn[i];
30   }
31   Point *array= new Point[totalnn];
32   Point *inarrayp= array;
33   for (i=0; i<4; i++) {
34     for (int a=0; a<nn[i]; a++) {
35       double fp= (double)a         / nn[i];
36       double fn= (double)(nn[i]-a) / nn[i];
37       *inarrayp++= p[i]*fn + p[(i+1)&3]*fp;
38     }
39   }
40   o.drawcell(array,totalnn);
41   delete[] array;
42 }                          
43
44 SortedCellList::Fragment* SortedCellList::insertfragment(int at) {
45   if (used==size) {
46     size+=5; size<<=1;
47     fragments= (Fragment**)realloc(fragments,sizeof(Fragment*)*size);
48     if (!fragments) { perror("realloc"); exit(1); }
49   }
50   memmove(fragments+at+1, fragments+at, sizeof(Fragment*)*(used-at));
51   used++;
52   Fragment *nf= new Fragment;
53   fragments[at]= nf;
54   return nf;
55 }
56
57 void SortedCellList::insert(Cell *it) {
58   double index= it->index();
59   int fragment;
60   for (fragment= used-1;
61        fragment >= 0 && index < fragments[fragment]->entries[0].index;
62        fragment--);
63   if (fragment < 0) {
64     Fragment *nf= insertfragment(0);
65     nf->used= 1;
66     nf->entries[0].index= index;
67     nf->entries[0].cell= it;
68     return;
69   }
70   int entry;
71   for (entry= 0;
72        entry < fragments[fragment]->used &&
73        index > fragments[fragment]->entries[entry].index;
74        entry++);
75   if (fragments[fragment]->used >= fragmentsize) {
76     Fragment *nf= insertfragment(fragment+1);
77     nf->used= fragmentsize>>1;
78     fragments[fragment]->used -= nf->used;
79     memcpy(nf->entries,
80            fragments[fragment]->entries + fragments[fragment]->used,
81            nf->used*sizeof(Entry));
82     if (entry >= fragments[fragment]->used) {
83       entry-= fragments[fragment]->used;
84       fragment++;
85     }
86   }
87   memmove(fragments[fragment]->entries + entry+1,
88           fragments[fragment]->entries + entry,
89           sizeof(Entry) * (fragments[fragment]->used - entry));
90   fragments[fragment]->entries[entry].index= index;
91   fragments[fragment]->entries[entry].cell= it;
92   fragments[fragment]->used++;
93 }
94
95 SortedCellList::~SortedCellList() {
96   for (int fragment=0; fragment<used; fragment++) {
97     for (int entry=0; entry<fragments[fragment]->used; entry++) {
98       delete fragments[fragment]->entries[entry].cell;
99     }
100     delete fragments[fragment];
101   }
102   free(fragments);
103 }
104
105 void SortedCellList::display(Output& o) {
106   o.startimage();
107   for (int fragment=0; fragment<used; fragment++) {
108     for (int entry=0; entry<fragments[fragment]->used; entry++) {
109       if (Point::indexvisible(fragments[fragment]->entries[entry].index)) {
110         fragments[fragment]->entries[entry].cell->display(o);
111       }
112     }
113   }
114   o.endimage();
115 }