dbf-udg

changeset 5:e09cbb2e9d4f

metaballs
author John Tsiombikas <nuclear@member.fsf.org>
date Mon, 18 Feb 2013 03:46:52 +0200
parents 5fb21401b7c8
children 57ea4988a9f2
files Makefile libs/metasurf/mcubes.h libs/metasurf/metasurf.c libs/metasurf/metasurf.h src/mballs.cc src/mballs.h src/udg.cc
diffstat 7 files changed, 1007 insertions(+), 53 deletions(-) [+]
line diff
     1.1 --- a/Makefile	Thu Feb 07 18:52:28 2013 +0200
     1.2 +++ b/Makefile	Mon Feb 18 03:46:52 2013 +0200
     1.3 @@ -1,12 +1,13 @@
     1.4 -csrc = $(wildcard src/*.c)
     1.5 +csrc = $(wildcard src/*.c) \
     1.6 +	   $(wildcard libs/metasurf/*.c)
     1.7  ccsrc = $(wildcard src/*.cc)
     1.8  obj = $(csrc:.c=.o) $(ccsrc:.cc=.o)
     1.9  dep = $(obj:.o=.d)
    1.10  bin = udg
    1.11  
    1.12 -CFLAGS = -pedantic -Wall -g
    1.13 +CFLAGS = -pedantic -Wall -g -O3 -Ilibs/metasurf
    1.14  CXXFLAGS = -std=c++11 $(CFLAGS)
    1.15 -LDFLAGS = $(libgl) -limago
    1.16 +LDFLAGS = $(libgl) -limago -lvmath
    1.17  
    1.18  ifeq ($(shell uname -s), Darwin)
    1.19  	libgl = -framework OpenGL -framework GLUT -lGLEW
     2.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     2.2 +++ b/libs/metasurf/mcubes.h	Mon Feb 18 03:46:52 2013 +0200
     2.3 @@ -0,0 +1,294 @@
     2.4 +static int mc_edge_table[256] = {
     2.5 +	0x0  , 0x109, 0x203, 0x30a, 0x406, 0x50f, 0x605, 0x70c,
     2.6 +	0x80c, 0x905, 0xa0f, 0xb06, 0xc0a, 0xd03, 0xe09, 0xf00,
     2.7 +	0x190, 0x99 , 0x393, 0x29a, 0x596, 0x49f, 0x795, 0x69c,
     2.8 +	0x99c, 0x895, 0xb9f, 0xa96, 0xd9a, 0xc93, 0xf99, 0xe90,
     2.9 +	0x230, 0x339, 0x33 , 0x13a, 0x636, 0x73f, 0x435, 0x53c,
    2.10 +	0xa3c, 0xb35, 0x83f, 0x936, 0xe3a, 0xf33, 0xc39, 0xd30,
    2.11 +	0x3a0, 0x2a9, 0x1a3, 0xaa , 0x7a6, 0x6af, 0x5a5, 0x4ac,
    2.12 +	0xbac, 0xaa5, 0x9af, 0x8a6, 0xfaa, 0xea3, 0xda9, 0xca0,
    2.13 +	0x460, 0x569, 0x663, 0x76a, 0x66 , 0x16f, 0x265, 0x36c,
    2.14 +	0xc6c, 0xd65, 0xe6f, 0xf66, 0x86a, 0x963, 0xa69, 0xb60,
    2.15 +	0x5f0, 0x4f9, 0x7f3, 0x6fa, 0x1f6, 0xff , 0x3f5, 0x2fc,
    2.16 +	0xdfc, 0xcf5, 0xfff, 0xef6, 0x9fa, 0x8f3, 0xbf9, 0xaf0,
    2.17 +	0x650, 0x759, 0x453, 0x55a, 0x256, 0x35f, 0x55 , 0x15c,
    2.18 +	0xe5c, 0xf55, 0xc5f, 0xd56, 0xa5a, 0xb53, 0x859, 0x950,
    2.19 +	0x7c0, 0x6c9, 0x5c3, 0x4ca, 0x3c6, 0x2cf, 0x1c5, 0xcc ,
    2.20 +	0xfcc, 0xec5, 0xdcf, 0xcc6, 0xbca, 0xac3, 0x9c9, 0x8c0,
    2.21 +	0x8c0, 0x9c9, 0xac3, 0xbca, 0xcc6, 0xdcf, 0xec5, 0xfcc,
    2.22 +	0xcc , 0x1c5, 0x2cf, 0x3c6, 0x4ca, 0x5c3, 0x6c9, 0x7c0,
    2.23 +	0x950, 0x859, 0xb53, 0xa5a, 0xd56, 0xc5f, 0xf55, 0xe5c,
    2.24 +	0x15c, 0x55 , 0x35f, 0x256, 0x55a, 0x453, 0x759, 0x650,
    2.25 +	0xaf0, 0xbf9, 0x8f3, 0x9fa, 0xef6, 0xfff, 0xcf5, 0xdfc,
    2.26 +	0x2fc, 0x3f5, 0xff , 0x1f6, 0x6fa, 0x7f3, 0x4f9, 0x5f0,
    2.27 +	0xb60, 0xa69, 0x963, 0x86a, 0xf66, 0xe6f, 0xd65, 0xc6c,
    2.28 +	0x36c, 0x265, 0x16f, 0x66 , 0x76a, 0x663, 0x569, 0x460,
    2.29 +	0xca0, 0xda9, 0xea3, 0xfaa, 0x8a6, 0x9af, 0xaa5, 0xbac,
    2.30 +	0x4ac, 0x5a5, 0x6af, 0x7a6, 0xaa , 0x1a3, 0x2a9, 0x3a0,
    2.31 +	0xd30, 0xc39, 0xf33, 0xe3a, 0x936, 0x83f, 0xb35, 0xa3c,
    2.32 +	0x53c, 0x435, 0x73f, 0x636, 0x13a, 0x33 , 0x339, 0x230,
    2.33 +	0xe90, 0xf99, 0xc93, 0xd9a, 0xa96, 0xb9f, 0x895, 0x99c,
    2.34 +	0x69c, 0x795, 0x49f, 0x596, 0x29a, 0x393, 0x99 , 0x190,
    2.35 +	0xf00, 0xe09, 0xd03, 0xc0a, 0xb06, 0xa0f, 0x905, 0x80c,
    2.36 +	0x70c, 0x605, 0x50f, 0x406, 0x30a, 0x203, 0x109, 0x0
    2.37 +};
    2.38 +
    2.39 +
    2.40 +static int mc_tri_table[256][16] = {
    2.41 +	{-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
    2.42 +	{0, 8, 3, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
    2.43 +	{0, 1, 9, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
    2.44 +	{1, 8, 3, 9, 8, 1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
    2.45 +	{1, 2, 10, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
    2.46 +	{0, 8, 3, 1, 2, 10, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
    2.47 +	{9, 2, 10, 0, 2, 9, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
    2.48 +	{2, 8, 3, 2, 10, 8, 10, 9, 8, -1, -1, -1, -1, -1, -1, -1},
    2.49 +	{3, 11, 2, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
    2.50 +	{0, 11, 2, 8, 11, 0, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
    2.51 +	{1, 9, 0, 2, 3, 11, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
    2.52 +	{1, 11, 2, 1, 9, 11, 9, 8, 11, -1, -1, -1, -1, -1, -1, -1},
    2.53 +	{3, 10, 1, 11, 10, 3, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
    2.54 +	{0, 10, 1, 0, 8, 10, 8, 11, 10, -1, -1, -1, -1, -1, -1, -1},
    2.55 +	{3, 9, 0, 3, 11, 9, 11, 10, 9, -1, -1, -1, -1, -1, -1, -1},
    2.56 +	{9, 8, 10, 10, 8, 11, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
    2.57 +	{4, 7, 8, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
    2.58 +	{4, 3, 0, 7, 3, 4, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
    2.59 +	{0, 1, 9, 8, 4, 7, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
    2.60 +	{4, 1, 9, 4, 7, 1, 7, 3, 1, -1, -1, -1, -1, -1, -1, -1},
    2.61 +	{1, 2, 10, 8, 4, 7, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
    2.62 +	{3, 4, 7, 3, 0, 4, 1, 2, 10, -1, -1, -1, -1, -1, -1, -1},
    2.63 +	{9, 2, 10, 9, 0, 2, 8, 4, 7, -1, -1, -1, -1, -1, -1, -1},
    2.64 +	{2, 10, 9, 2, 9, 7, 2, 7, 3, 7, 9, 4, -1, -1, -1, -1},
    2.65 +	{8, 4, 7, 3, 11, 2, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
    2.66 +	{11, 4, 7, 11, 2, 4, 2, 0, 4, -1, -1, -1, -1, -1, -1, -1},
    2.67 +	{9, 0, 1, 8, 4, 7, 2, 3, 11, -1, -1, -1, -1, -1, -1, -1},
    2.68 +	{4, 7, 11, 9, 4, 11, 9, 11, 2, 9, 2, 1, -1, -1, -1, -1},
    2.69 +	{3, 10, 1, 3, 11, 10, 7, 8, 4, -1, -1, -1, -1, -1, -1, -1},
    2.70 +	{1, 11, 10, 1, 4, 11, 1, 0, 4, 7, 11, 4, -1, -1, -1, -1},
    2.71 +	{4, 7, 8, 9, 0, 11, 9, 11, 10, 11, 0, 3, -1, -1, -1, -1},
    2.72 +	{4, 7, 11, 4, 11, 9, 9, 11, 10, -1, -1, -1, -1, -1, -1, -1},
    2.73 +	{9, 5, 4, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
    2.74 +	{9, 5, 4, 0, 8, 3, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
    2.75 +	{0, 5, 4, 1, 5, 0, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
    2.76 +	{8, 5, 4, 8, 3, 5, 3, 1, 5, -1, -1, -1, -1, -1, -1, -1},
    2.77 +	{1, 2, 10, 9, 5, 4, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
    2.78 +	{3, 0, 8, 1, 2, 10, 4, 9, 5, -1, -1, -1, -1, -1, -1, -1},
    2.79 +	{5, 2, 10, 5, 4, 2, 4, 0, 2, -1, -1, -1, -1, -1, -1, -1},
    2.80 +	{2, 10, 5, 3, 2, 5, 3, 5, 4, 3, 4, 8, -1, -1, -1, -1},
    2.81 +	{9, 5, 4, 2, 3, 11, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
    2.82 +	{0, 11, 2, 0, 8, 11, 4, 9, 5, -1, -1, -1, -1, -1, -1, -1},
    2.83 +	{0, 5, 4, 0, 1, 5, 2, 3, 11, -1, -1, -1, -1, -1, -1, -1},
    2.84 +	{2, 1, 5, 2, 5, 8, 2, 8, 11, 4, 8, 5, -1, -1, -1, -1},
    2.85 +	{10, 3, 11, 10, 1, 3, 9, 5, 4, -1, -1, -1, -1, -1, -1, -1},
    2.86 +	{4, 9, 5, 0, 8, 1, 8, 10, 1, 8, 11, 10, -1, -1, -1, -1},
    2.87 +	{5, 4, 0, 5, 0, 11, 5, 11, 10, 11, 0, 3, -1, -1, -1, -1},
    2.88 +	{5, 4, 8, 5, 8, 10, 10, 8, 11, -1, -1, -1, -1, -1, -1, -1},
    2.89 +	{9, 7, 8, 5, 7, 9, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
    2.90 +	{9, 3, 0, 9, 5, 3, 5, 7, 3, -1, -1, -1, -1, -1, -1, -1},
    2.91 +	{0, 7, 8, 0, 1, 7, 1, 5, 7, -1, -1, -1, -1, -1, -1, -1},
    2.92 +	{1, 5, 3, 3, 5, 7, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
    2.93 +	{9, 7, 8, 9, 5, 7, 10, 1, 2, -1, -1, -1, -1, -1, -1, -1},
    2.94 +	{10, 1, 2, 9, 5, 0, 5, 3, 0, 5, 7, 3, -1, -1, -1, -1},
    2.95 +	{8, 0, 2, 8, 2, 5, 8, 5, 7, 10, 5, 2, -1, -1, -1, -1},
    2.96 +	{2, 10, 5, 2, 5, 3, 3, 5, 7, -1, -1, -1, -1, -1, -1, -1},
    2.97 +	{7, 9, 5, 7, 8, 9, 3, 11, 2, -1, -1, -1, -1, -1, -1, -1},
    2.98 +	{9, 5, 7, 9, 7, 2, 9, 2, 0, 2, 7, 11, -1, -1, -1, -1},
    2.99 +	{2, 3, 11, 0, 1, 8, 1, 7, 8, 1, 5, 7, -1, -1, -1, -1},
   2.100 +	{11, 2, 1, 11, 1, 7, 7, 1, 5, -1, -1, -1, -1, -1, -1, -1},
   2.101 +	{9, 5, 8, 8, 5, 7, 10, 1, 3, 10, 3, 11, -1, -1, -1, -1},
   2.102 +	{5, 7, 0, 5, 0, 9, 7, 11, 0, 1, 0, 10, 11, 10, 0, -1},
   2.103 +	{11, 10, 0, 11, 0, 3, 10, 5, 0, 8, 0, 7, 5, 7, 0, -1},
   2.104 +	{11, 10, 5, 7, 11, 5, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.105 +	{10, 6, 5, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.106 +	{0, 8, 3, 5, 10, 6, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.107 +	{9, 0, 1, 5, 10, 6, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.108 +	{1, 8, 3, 1, 9, 8, 5, 10, 6, -1, -1, -1, -1, -1, -1, -1},
   2.109 +	{1, 6, 5, 2, 6, 1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.110 +	{1, 6, 5, 1, 2, 6, 3, 0, 8, -1, -1, -1, -1, -1, -1, -1},
   2.111 +	{9, 6, 5, 9, 0, 6, 0, 2, 6, -1, -1, -1, -1, -1, -1, -1},
   2.112 +	{5, 9, 8, 5, 8, 2, 5, 2, 6, 3, 2, 8, -1, -1, -1, -1},
   2.113 +	{2, 3, 11, 10, 6, 5, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.114 +	{11, 0, 8, 11, 2, 0, 10, 6, 5, -1, -1, -1, -1, -1, -1, -1},
   2.115 +	{0, 1, 9, 2, 3, 11, 5, 10, 6, -1, -1, -1, -1, -1, -1, -1},
   2.116 +	{5, 10, 6, 1, 9, 2, 9, 11, 2, 9, 8, 11, -1, -1, -1, -1},
   2.117 +	{6, 3, 11, 6, 5, 3, 5, 1, 3, -1, -1, -1, -1, -1, -1, -1},
   2.118 +	{0, 8, 11, 0, 11, 5, 0, 5, 1, 5, 11, 6, -1, -1, -1, -1},
   2.119 +	{3, 11, 6, 0, 3, 6, 0, 6, 5, 0, 5, 9, -1, -1, -1, -1},
   2.120 +	{6, 5, 9, 6, 9, 11, 11, 9, 8, -1, -1, -1, -1, -1, -1, -1},
   2.121 +	{5, 10, 6, 4, 7, 8, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.122 +	{4, 3, 0, 4, 7, 3, 6, 5, 10, -1, -1, -1, -1, -1, -1, -1},
   2.123 +	{1, 9, 0, 5, 10, 6, 8, 4, 7, -1, -1, -1, -1, -1, -1, -1},
   2.124 +	{10, 6, 5, 1, 9, 7, 1, 7, 3, 7, 9, 4, -1, -1, -1, -1},
   2.125 +	{6, 1, 2, 6, 5, 1, 4, 7, 8, -1, -1, -1, -1, -1, -1, -1},
   2.126 +	{1, 2, 5, 5, 2, 6, 3, 0, 4, 3, 4, 7, -1, -1, -1, -1},
   2.127 +	{8, 4, 7, 9, 0, 5, 0, 6, 5, 0, 2, 6, -1, -1, -1, -1},
   2.128 +	{7, 3, 9, 7, 9, 4, 3, 2, 9, 5, 9, 6, 2, 6, 9, -1},
   2.129 +	{3, 11, 2, 7, 8, 4, 10, 6, 5, -1, -1, -1, -1, -1, -1, -1},
   2.130 +	{5, 10, 6, 4, 7, 2, 4, 2, 0, 2, 7, 11, -1, -1, -1, -1},
   2.131 +	{0, 1, 9, 4, 7, 8, 2, 3, 11, 5, 10, 6, -1, -1, -1, -1},
   2.132 +	{9, 2, 1, 9, 11, 2, 9, 4, 11, 7, 11, 4, 5, 10, 6, -1},
   2.133 +	{8, 4, 7, 3, 11, 5, 3, 5, 1, 5, 11, 6, -1, -1, -1, -1},
   2.134 +	{5, 1, 11, 5, 11, 6, 1, 0, 11, 7, 11, 4, 0, 4, 11, -1},
   2.135 +	{0, 5, 9, 0, 6, 5, 0, 3, 6, 11, 6, 3, 8, 4, 7, -1},
   2.136 +	{6, 5, 9, 6, 9, 11, 4, 7, 9, 7, 11, 9, -1, -1, -1, -1},
   2.137 +	{10, 4, 9, 6, 4, 10, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.138 +	{4, 10, 6, 4, 9, 10, 0, 8, 3, -1, -1, -1, -1, -1, -1, -1},
   2.139 +	{10, 0, 1, 10, 6, 0, 6, 4, 0, -1, -1, -1, -1, -1, -1, -1},
   2.140 +	{8, 3, 1, 8, 1, 6, 8, 6, 4, 6, 1, 10, -1, -1, -1, -1},
   2.141 +	{1, 4, 9, 1, 2, 4, 2, 6, 4, -1, -1, -1, -1, -1, -1, -1},
   2.142 +	{3, 0, 8, 1, 2, 9, 2, 4, 9, 2, 6, 4, -1, -1, -1, -1},
   2.143 +	{0, 2, 4, 4, 2, 6, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.144 +	{8, 3, 2, 8, 2, 4, 4, 2, 6, -1, -1, -1, -1, -1, -1, -1},
   2.145 +	{10, 4, 9, 10, 6, 4, 11, 2, 3, -1, -1, -1, -1, -1, -1, -1},
   2.146 +	{0, 8, 2, 2, 8, 11, 4, 9, 10, 4, 10, 6, -1, -1, -1, -1},
   2.147 +	{3, 11, 2, 0, 1, 6, 0, 6, 4, 6, 1, 10, -1, -1, -1, -1},
   2.148 +	{6, 4, 1, 6, 1, 10, 4, 8, 1, 2, 1, 11, 8, 11, 1, -1},
   2.149 +	{9, 6, 4, 9, 3, 6, 9, 1, 3, 11, 6, 3, -1, -1, -1, -1},
   2.150 +	{8, 11, 1, 8, 1, 0, 11, 6, 1, 9, 1, 4, 6, 4, 1, -1},
   2.151 +	{3, 11, 6, 3, 6, 0, 0, 6, 4, -1, -1, -1, -1, -1, -1, -1},
   2.152 +	{6, 4, 8, 11, 6, 8, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.153 +	{7, 10, 6, 7, 8, 10, 8, 9, 10, -1, -1, -1, -1, -1, -1, -1},
   2.154 +	{0, 7, 3, 0, 10, 7, 0, 9, 10, 6, 7, 10, -1, -1, -1, -1},
   2.155 +	{10, 6, 7, 1, 10, 7, 1, 7, 8, 1, 8, 0, -1, -1, -1, -1},
   2.156 +	{10, 6, 7, 10, 7, 1, 1, 7, 3, -1, -1, -1, -1, -1, -1, -1},
   2.157 +	{1, 2, 6, 1, 6, 8, 1, 8, 9, 8, 6, 7, -1, -1, -1, -1},
   2.158 +	{2, 6, 9, 2, 9, 1, 6, 7, 9, 0, 9, 3, 7, 3, 9, -1},
   2.159 +	{7, 8, 0, 7, 0, 6, 6, 0, 2, -1, -1, -1, -1, -1, -1, -1},
   2.160 +	{7, 3, 2, 6, 7, 2, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.161 +	{2, 3, 11, 10, 6, 8, 10, 8, 9, 8, 6, 7, -1, -1, -1, -1},
   2.162 +	{2, 0, 7, 2, 7, 11, 0, 9, 7, 6, 7, 10, 9, 10, 7, -1},
   2.163 +	{1, 8, 0, 1, 7, 8, 1, 10, 7, 6, 7, 10, 2, 3, 11, -1},
   2.164 +	{11, 2, 1, 11, 1, 7, 10, 6, 1, 6, 7, 1, -1, -1, -1, -1},
   2.165 +	{8, 9, 6, 8, 6, 7, 9, 1, 6, 11, 6, 3, 1, 3, 6, -1},
   2.166 +	{0, 9, 1, 11, 6, 7, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.167 +	{7, 8, 0, 7, 0, 6, 3, 11, 0, 11, 6, 0, -1, -1, -1, -1},
   2.168 +	{7, 11, 6, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.169 +	{7, 6, 11, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.170 +	{3, 0, 8, 11, 7, 6, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.171 +	{0, 1, 9, 11, 7, 6, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.172 +	{8, 1, 9, 8, 3, 1, 11, 7, 6, -1, -1, -1, -1, -1, -1, -1},
   2.173 +	{10, 1, 2, 6, 11, 7, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.174 +	{1, 2, 10, 3, 0, 8, 6, 11, 7, -1, -1, -1, -1, -1, -1, -1},
   2.175 +	{2, 9, 0, 2, 10, 9, 6, 11, 7, -1, -1, -1, -1, -1, -1, -1},
   2.176 +	{6, 11, 7, 2, 10, 3, 10, 8, 3, 10, 9, 8, -1, -1, -1, -1},
   2.177 +	{7, 2, 3, 6, 2, 7, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.178 +	{7, 0, 8, 7, 6, 0, 6, 2, 0, -1, -1, -1, -1, -1, -1, -1},
   2.179 +	{2, 7, 6, 2, 3, 7, 0, 1, 9, -1, -1, -1, -1, -1, -1, -1},
   2.180 +	{1, 6, 2, 1, 8, 6, 1, 9, 8, 8, 7, 6, -1, -1, -1, -1},
   2.181 +	{10, 7, 6, 10, 1, 7, 1, 3, 7, -1, -1, -1, -1, -1, -1, -1},
   2.182 +	{10, 7, 6, 1, 7, 10, 1, 8, 7, 1, 0, 8, -1, -1, -1, -1},
   2.183 +	{0, 3, 7, 0, 7, 10, 0, 10, 9, 6, 10, 7, -1, -1, -1, -1},
   2.184 +	{7, 6, 10, 7, 10, 8, 8, 10, 9, -1, -1, -1, -1, -1, -1, -1},
   2.185 +	{6, 8, 4, 11, 8, 6, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.186 +	{3, 6, 11, 3, 0, 6, 0, 4, 6, -1, -1, -1, -1, -1, -1, -1},
   2.187 +	{8, 6, 11, 8, 4, 6, 9, 0, 1, -1, -1, -1, -1, -1, -1, -1},
   2.188 +	{9, 4, 6, 9, 6, 3, 9, 3, 1, 11, 3, 6, -1, -1, -1, -1},
   2.189 +	{6, 8, 4, 6, 11, 8, 2, 10, 1, -1, -1, -1, -1, -1, -1, -1},
   2.190 +	{1, 2, 10, 3, 0, 11, 0, 6, 11, 0, 4, 6, -1, -1, -1, -1},
   2.191 +	{4, 11, 8, 4, 6, 11, 0, 2, 9, 2, 10, 9, -1, -1, -1, -1},
   2.192 +	{10, 9, 3, 10, 3, 2, 9, 4, 3, 11, 3, 6, 4, 6, 3, -1},
   2.193 +	{8, 2, 3, 8, 4, 2, 4, 6, 2, -1, -1, -1, -1, -1, -1, -1},
   2.194 +	{0, 4, 2, 4, 6, 2, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.195 +	{1, 9, 0, 2, 3, 4, 2, 4, 6, 4, 3, 8, -1, -1, -1, -1},
   2.196 +	{1, 9, 4, 1, 4, 2, 2, 4, 6, -1, -1, -1, -1, -1, -1, -1},
   2.197 +	{8, 1, 3, 8, 6, 1, 8, 4, 6, 6, 10, 1, -1, -1, -1, -1},
   2.198 +	{10, 1, 0, 10, 0, 6, 6, 0, 4, -1, -1, -1, -1, -1, -1, -1},
   2.199 +	{4, 6, 3, 4, 3, 8, 6, 10, 3, 0, 3, 9, 10, 9, 3, -1},
   2.200 +	{10, 9, 4, 6, 10, 4, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.201 +	{4, 9, 5, 7, 6, 11, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.202 +	{0, 8, 3, 4, 9, 5, 11, 7, 6, -1, -1, -1, -1, -1, -1, -1},
   2.203 +	{5, 0, 1, 5, 4, 0, 7, 6, 11, -1, -1, -1, -1, -1, -1, -1},
   2.204 +	{11, 7, 6, 8, 3, 4, 3, 5, 4, 3, 1, 5, -1, -1, -1, -1},
   2.205 +	{9, 5, 4, 10, 1, 2, 7, 6, 11, -1, -1, -1, -1, -1, -1, -1},
   2.206 +	{6, 11, 7, 1, 2, 10, 0, 8, 3, 4, 9, 5, -1, -1, -1, -1},
   2.207 +	{7, 6, 11, 5, 4, 10, 4, 2, 10, 4, 0, 2, -1, -1, -1, -1},
   2.208 +	{3, 4, 8, 3, 5, 4, 3, 2, 5, 10, 5, 2, 11, 7, 6, -1},
   2.209 +	{7, 2, 3, 7, 6, 2, 5, 4, 9, -1, -1, -1, -1, -1, -1, -1},
   2.210 +	{9, 5, 4, 0, 8, 6, 0, 6, 2, 6, 8, 7, -1, -1, -1, -1},
   2.211 +	{3, 6, 2, 3, 7, 6, 1, 5, 0, 5, 4, 0, -1, -1, -1, -1},
   2.212 +	{6, 2, 8, 6, 8, 7, 2, 1, 8, 4, 8, 5, 1, 5, 8, -1},
   2.213 +	{9, 5, 4, 10, 1, 6, 1, 7, 6, 1, 3, 7, -1, -1, -1, -1},
   2.214 +	{1, 6, 10, 1, 7, 6, 1, 0, 7, 8, 7, 0, 9, 5, 4, -1},
   2.215 +	{4, 0, 10, 4, 10, 5, 0, 3, 10, 6, 10, 7, 3, 7, 10, -1},
   2.216 +	{7, 6, 10, 7, 10, 8, 5, 4, 10, 4, 8, 10, -1, -1, -1, -1},
   2.217 +	{6, 9, 5, 6, 11, 9, 11, 8, 9, -1, -1, -1, -1, -1, -1, -1},
   2.218 +	{3, 6, 11, 0, 6, 3, 0, 5, 6, 0, 9, 5, -1, -1, -1, -1},
   2.219 +	{0, 11, 8, 0, 5, 11, 0, 1, 5, 5, 6, 11, -1, -1, -1, -1},
   2.220 +	{6, 11, 3, 6, 3, 5, 5, 3, 1, -1, -1, -1, -1, -1, -1, -1},
   2.221 +	{1, 2, 10, 9, 5, 11, 9, 11, 8, 11, 5, 6, -1, -1, -1, -1},
   2.222 +	{0, 11, 3, 0, 6, 11, 0, 9, 6, 5, 6, 9, 1, 2, 10, -1},
   2.223 +	{11, 8, 5, 11, 5, 6, 8, 0, 5, 10, 5, 2, 0, 2, 5, -1},
   2.224 +	{6, 11, 3, 6, 3, 5, 2, 10, 3, 10, 5, 3, -1, -1, -1, -1},
   2.225 +	{5, 8, 9, 5, 2, 8, 5, 6, 2, 3, 8, 2, -1, -1, -1, -1},
   2.226 +	{9, 5, 6, 9, 6, 0, 0, 6, 2, -1, -1, -1, -1, -1, -1, -1},
   2.227 +	{1, 5, 8, 1, 8, 0, 5, 6, 8, 3, 8, 2, 6, 2, 8, -1},
   2.228 +	{1, 5, 6, 2, 1, 6, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.229 +	{1, 3, 6, 1, 6, 10, 3, 8, 6, 5, 6, 9, 8, 9, 6, -1},
   2.230 +	{10, 1, 0, 10, 0, 6, 9, 5, 0, 5, 6, 0, -1, -1, -1, -1},
   2.231 +	{0, 3, 8, 5, 6, 10, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.232 +	{10, 5, 6, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.233 +	{11, 5, 10, 7, 5, 11, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.234 +	{11, 5, 10, 11, 7, 5, 8, 3, 0, -1, -1, -1, -1, -1, -1, -1},
   2.235 +	{5, 11, 7, 5, 10, 11, 1, 9, 0, -1, -1, -1, -1, -1, -1, -1},
   2.236 +	{10, 7, 5, 10, 11, 7, 9, 8, 1, 8, 3, 1, -1, -1, -1, -1},
   2.237 +	{11, 1, 2, 11, 7, 1, 7, 5, 1, -1, -1, -1, -1, -1, -1, -1},
   2.238 +	{0, 8, 3, 1, 2, 7, 1, 7, 5, 7, 2, 11, -1, -1, -1, -1},
   2.239 +	{9, 7, 5, 9, 2, 7, 9, 0, 2, 2, 11, 7, -1, -1, -1, -1},
   2.240 +	{7, 5, 2, 7, 2, 11, 5, 9, 2, 3, 2, 8, 9, 8, 2, -1},
   2.241 +	{2, 5, 10, 2, 3, 5, 3, 7, 5, -1, -1, -1, -1, -1, -1, -1},
   2.242 +	{8, 2, 0, 8, 5, 2, 8, 7, 5, 10, 2, 5, -1, -1, -1, -1},
   2.243 +	{9, 0, 1, 5, 10, 3, 5, 3, 7, 3, 10, 2, -1, -1, -1, -1},
   2.244 +	{9, 8, 2, 9, 2, 1, 8, 7, 2, 10, 2, 5, 7, 5, 2, -1},
   2.245 +	{1, 3, 5, 3, 7, 5, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.246 +	{0, 8, 7, 0, 7, 1, 1, 7, 5, -1, -1, -1, -1, -1, -1, -1},
   2.247 +	{9, 0, 3, 9, 3, 5, 5, 3, 7, -1, -1, -1, -1, -1, -1, -1},
   2.248 +	{9, 8, 7, 5, 9, 7, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.249 +	{5, 8, 4, 5, 10, 8, 10, 11, 8, -1, -1, -1, -1, -1, -1, -1},
   2.250 +	{5, 0, 4, 5, 11, 0, 5, 10, 11, 11, 3, 0, -1, -1, -1, -1},
   2.251 +	{0, 1, 9, 8, 4, 10, 8, 10, 11, 10, 4, 5, -1, -1, -1, -1},
   2.252 +	{10, 11, 4, 10, 4, 5, 11, 3, 4, 9, 4, 1, 3, 1, 4, -1},
   2.253 +	{2, 5, 1, 2, 8, 5, 2, 11, 8, 4, 5, 8, -1, -1, -1, -1},
   2.254 +	{0, 4, 11, 0, 11, 3, 4, 5, 11, 2, 11, 1, 5, 1, 11, -1},
   2.255 +	{0, 2, 5, 0, 5, 9, 2, 11, 5, 4, 5, 8, 11, 8, 5, -1},
   2.256 +	{9, 4, 5, 2, 11, 3, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.257 +	{2, 5, 10, 3, 5, 2, 3, 4, 5, 3, 8, 4, -1, -1, -1, -1},
   2.258 +	{5, 10, 2, 5, 2, 4, 4, 2, 0, -1, -1, -1, -1, -1, -1, -1},
   2.259 +	{3, 10, 2, 3, 5, 10, 3, 8, 5, 4, 5, 8, 0, 1, 9, -1},
   2.260 +	{5, 10, 2, 5, 2, 4, 1, 9, 2, 9, 4, 2, -1, -1, -1, -1},
   2.261 +	{8, 4, 5, 8, 5, 3, 3, 5, 1, -1, -1, -1, -1, -1, -1, -1},
   2.262 +	{0, 4, 5, 1, 0, 5, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.263 +	{8, 4, 5, 8, 5, 3, 9, 0, 5, 0, 3, 5, -1, -1, -1, -1},
   2.264 +	{9, 4, 5, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.265 +	{4, 11, 7, 4, 9, 11, 9, 10, 11, -1, -1, -1, -1, -1, -1, -1},
   2.266 +	{0, 8, 3, 4, 9, 7, 9, 11, 7, 9, 10, 11, -1, -1, -1, -1},
   2.267 +	{1, 10, 11, 1, 11, 4, 1, 4, 0, 7, 4, 11, -1, -1, -1, -1},
   2.268 +	{3, 1, 4, 3, 4, 8, 1, 10, 4, 7, 4, 11, 10, 11, 4, -1},
   2.269 +	{4, 11, 7, 9, 11, 4, 9, 2, 11, 9, 1, 2, -1, -1, -1, -1},
   2.270 +	{9, 7, 4, 9, 11, 7, 9, 1, 11, 2, 11, 1, 0, 8, 3, -1},
   2.271 +	{11, 7, 4, 11, 4, 2, 2, 4, 0, -1, -1, -1, -1, -1, -1, -1},
   2.272 +	{11, 7, 4, 11, 4, 2, 8, 3, 4, 3, 2, 4, -1, -1, -1, -1},
   2.273 +	{2, 9, 10, 2, 7, 9, 2, 3, 7, 7, 4, 9, -1, -1, -1, -1},
   2.274 +	{9, 10, 7, 9, 7, 4, 10, 2, 7, 8, 7, 0, 2, 0, 7, -1},
   2.275 +	{3, 7, 10, 3, 10, 2, 7, 4, 10, 1, 10, 0, 4, 0, 10, -1},
   2.276 +	{1, 10, 2, 8, 7, 4, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.277 +	{4, 9, 1, 4, 1, 7, 7, 1, 3, -1, -1, -1, -1, -1, -1, -1},
   2.278 +	{4, 9, 1, 4, 1, 7, 0, 8, 1, 8, 7, 1, -1, -1, -1, -1},
   2.279 +	{4, 0, 3, 7, 4, 3, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.280 +	{4, 8, 7, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.281 +	{9, 10, 8, 10, 11, 8, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.282 +	{3, 0, 9, 3, 9, 11, 11, 9, 10, -1, -1, -1, -1, -1, -1, -1},
   2.283 +	{0, 1, 10, 0, 10, 8, 8, 10, 11, -1, -1, -1, -1, -1, -1, -1},
   2.284 +	{3, 1, 10, 11, 3, 10, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.285 +	{1, 2, 11, 1, 11, 9, 9, 11, 8, -1, -1, -1, -1, -1, -1, -1},
   2.286 +	{3, 0, 9, 3, 9, 11, 1, 2, 9, 2, 11, 9, -1, -1, -1, -1},
   2.287 +	{0, 2, 11, 8, 0, 11, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.288 +	{3, 2, 11, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.289 +	{2, 3, 8, 2, 8, 10, 10, 8, 9, -1, -1, -1, -1, -1, -1, -1},
   2.290 +	{9, 10, 2, 0, 9, 2, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.291 +	{2, 3, 8, 2, 8, 10, 0, 1, 8, 1, 10, 8, -1, -1, -1, -1},
   2.292 +	{1, 10, 2, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.293 +	{1, 3, 8, 9, 1, 8, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.294 +	{0, 9, 1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.295 +	{0, 3, 8, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1},
   2.296 +	{-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1}
   2.297 +};
     3.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     3.2 +++ b/libs/metasurf/metasurf.c	Mon Feb 18 03:46:52 2013 +0200
     3.3 @@ -0,0 +1,413 @@
     3.4 +/*
     3.5 +metasurf - a library for implicit surface polygonization
     3.6 +Copyright (C) 2011  John Tsiombikas <nuclear@member.fsf.org>
     3.7 +
     3.8 +This program is free software: you can redistribute it and/or modify
     3.9 +it under the terms of the GNU Lesser General Public License as published by
    3.10 +the Free Software Foundation, either version 3 of the License, or
    3.11 +(at your option) any later version.
    3.12 +
    3.13 +This program is distributed in the hope that it will be useful,
    3.14 +but WITHOUT ANY WARRANTY; without even the implied warranty of
    3.15 +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    3.16 +GNU Lesser General Public License for more details.
    3.17 +
    3.18 +You should have received a copy of the GNU Lesser General Public License
    3.19 +along with this program.  If not, see <http://www.gnu.org/licenses/>.
    3.20 +*/
    3.21 +#include <stdio.h>
    3.22 +#include <stdlib.h>
    3.23 +#include "metasurf.h"
    3.24 +#include "mcubes.h"
    3.25 +
    3.26 +#undef USE_MTETRA
    3.27 +#define USE_MCUBES
    3.28 +
    3.29 +#if (defined(USE_MTETRA) && defined(USE_MCUBES)) || (!defined(USE_MTETRA) && !defined(USE_MCUBES))
    3.30 +#error "pick either USE_MTETRA or USE_MCUBES, not both..."
    3.31 +#endif
    3.32 +
    3.33 +typedef float vec3[3];
    3.34 +
    3.35 +struct metasurface {
    3.36 +	vec3 min, max;
    3.37 +	int res[3];
    3.38 +	float thres;
    3.39 +
    3.40 +	msurf_eval_func_t eval;
    3.41 +	msurf_vertex_func_t vertex;
    3.42 +	msurf_normal_func_t normal;
    3.43 +
    3.44 +	float dx, dy, dz;
    3.45 +	int flip;
    3.46 +
    3.47 +	vec3 vbuf[3];
    3.48 +	int nverts;
    3.49 +};
    3.50 +
    3.51 +static int msurf_init(struct metasurface *ms);
    3.52 +static void process_cell(struct metasurface *ms, vec3 pos, vec3 sz);
    3.53 +#ifdef USE_MTETRA
    3.54 +static void process_tetra(struct metasurface *ms, int *idx, vec3 *pos, float *val);
    3.55 +#endif
    3.56 +#ifdef USE_MCUBES
    3.57 +static void process_cube(struct metasurface *ms, vec3 *pos, float *val);
    3.58 +#endif
    3.59 +
    3.60 +
    3.61 +struct metasurface *msurf_create(void)
    3.62 +{
    3.63 +	struct metasurface *ms;
    3.64 +
    3.65 +	if(!(ms = malloc(sizeof *ms))) {
    3.66 +		return 0;
    3.67 +	}
    3.68 +	if(msurf_init(ms) == -1) {
    3.69 +		free(ms);
    3.70 +	}
    3.71 +	return ms;
    3.72 +}
    3.73 +
    3.74 +void msurf_free(struct metasurface *ms)
    3.75 +{
    3.76 +	free(ms);
    3.77 +}
    3.78 +
    3.79 +static int msurf_init(struct metasurface *ms)
    3.80 +{
    3.81 +	ms->thres = 0.0;
    3.82 +	ms->eval = 0;
    3.83 +	ms->vertex = 0;
    3.84 +	ms->normal = 0;
    3.85 +	ms->min[0] = ms->min[1] = ms->min[2] = -1.0;
    3.86 +	ms->max[0] = ms->max[1] = ms->max[2] = 1.0;
    3.87 +	ms->res[0] = ms->res[1] = ms->res[2] = 40;
    3.88 +	ms->nverts = 0;
    3.89 +
    3.90 +	ms->dx = ms->dy = ms->dz = 0.001;
    3.91 +	ms->flip = 0;
    3.92 +
    3.93 +	return 0;
    3.94 +}
    3.95 +
    3.96 +void msurf_inside(struct metasurface *ms, int inside)
    3.97 +{
    3.98 +	switch(inside) {
    3.99 +	case MSURF_GREATER:
   3.100 +		ms->flip = 0;
   3.101 +		break;
   3.102 +
   3.103 +	case MSURF_LESS:
   3.104 +		ms->flip = 1;
   3.105 +		break;
   3.106 +
   3.107 +	default:
   3.108 +		fprintf(stderr, "msurf_inside expects MSURF_GREATER or MSURF_LESS\n");
   3.109 +	}
   3.110 +}
   3.111 +
   3.112 +void msurf_eval_func(struct metasurface *ms, msurf_eval_func_t func)
   3.113 +{
   3.114 +	ms->eval = func;
   3.115 +}
   3.116 +
   3.117 +void msurf_vertex_func(struct metasurface *ms, msurf_vertex_func_t func)
   3.118 +{
   3.119 +	ms->vertex = func;
   3.120 +}
   3.121 +
   3.122 +void msurf_normal_func(struct metasurface *ms, msurf_normal_func_t func)
   3.123 +{
   3.124 +	ms->normal = func;
   3.125 +}
   3.126 +
   3.127 +void msurf_bounds(struct metasurface *ms, float xmin, float ymin, float zmin, float xmax, float ymax, float zmax)
   3.128 +{
   3.129 +	ms->min[0] = xmin;
   3.130 +	ms->min[1] = ymin;
   3.131 +	ms->min[2] = zmin;
   3.132 +	ms->max[0] = xmax;
   3.133 +	ms->max[1] = ymax;
   3.134 +	ms->max[2] = zmax;
   3.135 +}
   3.136 +
   3.137 +void msurf_resolution(struct metasurface *ms, int xres, int yres, int zres)
   3.138 +{
   3.139 +	ms->res[0] = xres;
   3.140 +	ms->res[1] = yres;
   3.141 +	ms->res[2] = zres;
   3.142 +}
   3.143 +
   3.144 +void msurf_threshold(struct metasurface *ms, float thres)
   3.145 +{
   3.146 +	ms->thres = thres;
   3.147 +}
   3.148 +
   3.149 +
   3.150 +int msurf_polygonize(struct metasurface *ms)
   3.151 +{
   3.152 +	int i, j, k;
   3.153 +	vec3 pos, delta;
   3.154 +
   3.155 +	if(!ms->eval || !ms->vertex) {
   3.156 +		fprintf(stderr, "you need to set eval and vertex callbacks before calling msurf_polygonize\n");
   3.157 +		return -1;
   3.158 +	}
   3.159 +
   3.160 +	for(i=0; i<3; i++) {
   3.161 +		delta[i] = (ms->max[i] - ms->min[i]) / (float)ms->res[i];
   3.162 +	}
   3.163 +
   3.164 +	pos[0] = ms->min[0];
   3.165 +	for(i=0; i<ms->res[0] - 1; i++) {
   3.166 +
   3.167 +		pos[1] = ms->min[1];
   3.168 +		for(j=0; j<ms->res[1] - 1; j++) {
   3.169 +
   3.170 +			pos[2] = ms->min[2];
   3.171 +			for(k=0; k<ms->res[2] - 1; k++) {
   3.172 +
   3.173 +				process_cell(ms, pos, delta);
   3.174 +
   3.175 +				pos[2] += delta[2];
   3.176 +			}
   3.177 +			pos[1] += delta[1];
   3.178 +		}
   3.179 +		pos[0] += delta[0];
   3.180 +	}
   3.181 +	return 0;
   3.182 +}
   3.183 +
   3.184 +
   3.185 +static void process_cell(struct metasurface *ms, vec3 pos, vec3 sz)
   3.186 +{
   3.187 +	int i;
   3.188 +	vec3 p[8];
   3.189 +	float val[8];
   3.190 +
   3.191 +#ifdef USE_MTETRA
   3.192 +	static int tetra[][4] = {
   3.193 +		{0, 2, 3, 7},
   3.194 +		{0, 2, 6, 7},
   3.195 +		{0, 4, 6, 7},
   3.196 +		{0, 6, 1, 2},
   3.197 +		{0, 6, 1, 4},
   3.198 +		{5, 6, 1, 4}
   3.199 +	};
   3.200 +#endif
   3.201 +
   3.202 +	static const float offs[][3] = {
   3.203 +		{0.0f, 0.0f, 0.0f},
   3.204 +		{1.0f, 0.0f, 0.0f},
   3.205 +		{1.0f, 1.0f, 0.0f},
   3.206 +		{0.0f, 1.0f, 0.0f},
   3.207 +		{0.0f, 0.0f, 1.0f},
   3.208 +		{1.0f, 0.0f, 1.0f},
   3.209 +		{1.0f, 1.0f, 1.0f},
   3.210 +		{0.0f, 1.0f, 1.0f}
   3.211 +	};
   3.212 +
   3.213 +	for(i=0; i<8; i++) {
   3.214 +		p[i][0] = pos[0] + sz[0] * offs[i][2];
   3.215 +		p[i][1] = pos[1] + sz[1] * offs[i][1];
   3.216 +		p[i][2] = pos[2] + sz[2] * offs[i][0];
   3.217 +
   3.218 +		val[i] = ms->eval(p[i][0], p[i][1], p[i][2]);
   3.219 +	}
   3.220 +
   3.221 +#ifdef USE_MTETRA
   3.222 +	for(i=0; i<6; i++) {
   3.223 +		process_tetra(ms, tetra[i], p, val);
   3.224 +	}
   3.225 +#endif
   3.226 +#ifdef USE_MCUBES
   3.227 +	process_cube(ms, p, val);
   3.228 +#endif
   3.229 +}
   3.230 +
   3.231 +
   3.232 +/* ---- marching cubes implementation ---- */
   3.233 +#ifdef USE_MCUBES
   3.234 +
   3.235 +static unsigned int mc_bitcode(float *val, float thres);
   3.236 +
   3.237 +static void process_cube(struct metasurface *ms, vec3 *pos, float *val)
   3.238 +{
   3.239 +	static const int pidx[12][2] = {
   3.240 +		{0, 1}, {1, 2}, {2, 3}, {3, 0}, {4, 5}, {5, 6},
   3.241 +		{6, 7},	{7, 4}, {0, 4}, {1, 5}, {2, 6}, {3, 7}
   3.242 +	};
   3.243 +	int i, j;
   3.244 +	vec3 vert[12];
   3.245 +	unsigned int code = mc_bitcode(val, ms->thres);
   3.246 +
   3.247 +	if(ms->flip) {
   3.248 +		code = ~code & 0xff;
   3.249 +	}
   3.250 +
   3.251 +	if(mc_edge_table[code] == 0) {
   3.252 +		return;
   3.253 +	}
   3.254 +
   3.255 +	for(i=0; i<12; i++) {
   3.256 +		if(mc_edge_table[code] & (1 << i)) {
   3.257 +			int p0 = pidx[i][0];
   3.258 +			int p1 = pidx[i][1];
   3.259 +
   3.260 +			float t = (ms->thres - val[p0]) / (val[p1] - val[p0]);
   3.261 +			vert[i][0] = pos[p0][0] + (pos[p1][0] - pos[p0][0]) * t;
   3.262 +			vert[i][1] = pos[p0][1] + (pos[p1][1] - pos[p0][1]) * t;
   3.263 +			vert[i][2] = pos[p0][2] + (pos[p1][2] - pos[p0][2]) * t;
   3.264 +		}
   3.265 +	}
   3.266 +
   3.267 +	for(i=0; mc_tri_table[code][i] != -1; i+=3) {
   3.268 +		for(j=0; j<3; j++) {
   3.269 +			float *v = vert[mc_tri_table[code][i + j]];
   3.270 +
   3.271 +			if(ms->normal) {
   3.272 +				float dfdx, dfdy, dfdz;
   3.273 +				dfdx = ms->eval(v[0] - ms->dx, v[1], v[2]) - ms->eval(v[0] + ms->dx, v[1], v[2]);
   3.274 +				dfdy = ms->eval(v[0], v[1] - ms->dy, v[2]) - ms->eval(v[0], v[1] + ms->dy, v[2]);
   3.275 +				dfdz = ms->eval(v[0], v[1], v[2] - ms->dz) - ms->eval(v[0], v[1], v[2] + ms->dz);
   3.276 +
   3.277 +				if(ms->flip) {
   3.278 +					dfdx = -dfdx;
   3.279 +					dfdy = -dfdy;
   3.280 +					dfdz = -dfdz;
   3.281 +				}
   3.282 +				ms->normal(dfdx, dfdy, dfdz);
   3.283 +			}
   3.284 +
   3.285 +			ms->vertex(v[0], v[1], v[2]);
   3.286 +		}
   3.287 +	}
   3.288 +}
   3.289 +
   3.290 +static unsigned int mc_bitcode(float *val, float thres)
   3.291 +{
   3.292 +	unsigned int i, res = 0;
   3.293 +
   3.294 +	for(i=0; i<8; i++) {
   3.295 +		if(val[i] > thres) {
   3.296 +			res |= 1 << i;
   3.297 +		}
   3.298 +	}
   3.299 +	return res;
   3.300 +}
   3.301 +#endif	/* USE_MCUBES */
   3.302 +
   3.303 +
   3.304 +/* ---- marching tetrahedra implementation (incomplete) ---- */
   3.305 +#ifdef USE_MTETRA
   3.306 +
   3.307 +static unsigned int mt_bitcode(float v0, float v1, float v2, float v3, float thres);
   3.308 +static void emmit(struct metasurface *ms, float v0, float v1, vec3 p0, vec3 p1, int rev)
   3.309 +
   3.310 +
   3.311 +#define REVBIT(x)	((x) & 8)
   3.312 +#define INV(x)		(~(x) & 0xf)
   3.313 +#define EDGE(a, b)	emmit(ms, val[idx[a]], val[idx[b]], pos[idx[a]], pos[idx[b]], REVBIT(code))
   3.314 +static void process_tetra(struct metasurface *ms, int *idx, vec3 *pos, float *val)
   3.315 +{
   3.316 +	unsigned int code = mt_bitcode(val[idx[0]], val[idx[1]], val[idx[2]], val[idx[3]], ms->thres);
   3.317 +
   3.318 +	switch(code) {
   3.319 +	case 1:
   3.320 +	case INV(1):
   3.321 +		EDGE(0, 1);
   3.322 +		EDGE(0, 2);
   3.323 +		EDGE(0, 3);
   3.324 +		break;
   3.325 +
   3.326 +	case 2:
   3.327 +	case INV(2):
   3.328 +		EDGE(1, 0);
   3.329 +		EDGE(1, 3);
   3.330 +		EDGE(1, 2);
   3.331 +		break;
   3.332 +
   3.333 +	case 3:
   3.334 +	case INV(3):
   3.335 +		EDGE(0, 3);
   3.336 +		EDGE(0, 2);
   3.337 +		EDGE(1, 3);
   3.338 +
   3.339 +		EDGE(1, 3);
   3.340 +		EDGE(1, 2);
   3.341 +		EDGE(0, 2);
   3.342 +		break;
   3.343 +
   3.344 +	case 4:
   3.345 +	case INV(4):
   3.346 +		EDGE(2, 0);
   3.347 +		EDGE(2, 1);
   3.348 +		EDGE(2, 3);
   3.349 +		break;
   3.350 +
   3.351 +	case 5:
   3.352 +	case INV(5):
   3.353 +		EDGE(0, 1);
   3.354 +		EDGE(2, 3);
   3.355 +		EDGE(0, 3);
   3.356 +
   3.357 +		EDGE(0, 1);
   3.358 +		EDGE(1, 2);
   3.359 +		EDGE(2, 3);
   3.360 +		break;
   3.361 +
   3.362 +	case 6:
   3.363 +	case INV(6):
   3.364 +		EDGE(0, 1);
   3.365 +		EDGE(1, 3);
   3.366 +		EDGE(2, 3);
   3.367 +
   3.368 +		EDGE(0, 1);
   3.369 +		EDGE(0, 2);
   3.370 +		EDGE(2, 3);
   3.371 +		break;
   3.372 +
   3.373 +	case 7:
   3.374 +	case INV(7):
   3.375 +		EDGE(3, 0);
   3.376 +		EDGE(3, 2);
   3.377 +		EDGE(3, 1);
   3.378 +		break;
   3.379 +
   3.380 +	default:
   3.381 +		break;	/* cases 0 and 15 */
   3.382 +	}
   3.383 +}
   3.384 +
   3.385 +#define BIT(i)	((v##i > thres) ? (1 << i) : 0)
   3.386 +static unsigned int mt_bitcode(float v0, float v1, float v2, float v3, float thres)
   3.387 +{
   3.388 +	return BIT(0) | BIT(1) | BIT(2) | BIT(3);
   3.389 +}
   3.390 +
   3.391 +static void emmit(struct metasurface *ms, float v0, float v1, vec3 p0, vec3 p1, int rev)
   3.392 +{
   3.393 +	int i;
   3.394 +	float t = (ms->thres - v0) / (v1 - v0);
   3.395 +
   3.396 +	vec3 p;
   3.397 +	for(i=0; i<3; i++) {
   3.398 +		p[i] = p0[i] + (p1[i] - p0[i]) * t;
   3.399 +	}
   3.400 +	ms->vertex(p[0], p[1], p[2]);
   3.401 +
   3.402 +	/*for(i=0; i<3; i++) {
   3.403 +		ms->vbuf[ms->nverts][i] = p0[i] + (p1[i] - p0[i]) * t;
   3.404 +	}
   3.405 +
   3.406 +	if(++ms->nverts >= 3) {
   3.407 +		ms->nverts = 0;
   3.408 +
   3.409 +		for(i=0; i<3; i++) {
   3.410 +			int idx = rev ? (2 - i) : i;
   3.411 +			ms->vertex(ms->vbuf[idx][0], ms->vbuf[idx][1], ms->vbuf[idx][2]);
   3.412 +		}
   3.413 +	}*/
   3.414 +}
   3.415 +
   3.416 +#endif	/* USE_MTETRA */
     4.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     4.2 +++ b/libs/metasurf/metasurf.h	Mon Feb 18 03:46:52 2013 +0200
     4.3 @@ -0,0 +1,72 @@
     4.4 +/*
     4.5 +metasurf - a library for implicit surface polygonization
     4.6 +Copyright (C) 2011  John Tsiombikas <nuclear@member.fsf.org>
     4.7 +
     4.8 +This program is free software: you can redistribute it and/or modify
     4.9 +it under the terms of the GNU Lesser General Public License as published by
    4.10 +the Free Software Foundation, either version 3 of the License, or
    4.11 +(at your option) any later version.
    4.12 +
    4.13 +This program is distributed in the hope that it will be useful,
    4.14 +but WITHOUT ANY WARRANTY; without even the implied warranty of
    4.15 +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    4.16 +GNU Lesser General Public License for more details.
    4.17 +
    4.18 +You should have received a copy of the GNU Lesser General Public License
    4.19 +along with this program.  If not, see <http://www.gnu.org/licenses/>.
    4.20 +*/
    4.21 +
    4.22 +#ifndef METASURF_H_
    4.23 +#define METASURF_H_
    4.24 +
    4.25 +#define MSURF_GREATER	1
    4.26 +#define MSURF_LESS		0
    4.27 +
    4.28 +struct metasurface;
    4.29 +
    4.30 +typedef float (*msurf_eval_func_t)(float, float, float);
    4.31 +typedef void (*msurf_vertex_func_t)(float, float, float);
    4.32 +typedef void (*msurf_normal_func_t)(float, float, float);
    4.33 +
    4.34 +#ifdef __cplusplus
    4.35 +extern "C" {
    4.36 +#endif
    4.37 +
    4.38 +struct metasurface *msurf_create(void);
    4.39 +void msurf_free(struct metasurface *ms);
    4.40 +
    4.41 +/* which is inside above or below the threshold */
    4.42 +void msurf_inside(struct metasurface *ms, int inside);
    4.43 +
    4.44 +/* set a scalar field evaluator function */
    4.45 +void msurf_eval_func(struct metasurface *ms, msurf_eval_func_t func);
    4.46 +
    4.47 +/* set a generated vertex callback function */
    4.48 +void msurf_vertex_func(struct metasurface *ms, msurf_vertex_func_t func);
    4.49 +
    4.50 +/* set a generated surface normal callback function (unused yet) */
    4.51 +void msurf_normal_func(struct metasurface *ms, msurf_normal_func_t func);
    4.52 +
    4.53 +/* set the bounding box (default: -1, -1, -1, 1, 1, 1)
    4.54 + * keep this as tight as possible to avoid wasting grid resolution
    4.55 + */
    4.56 +void msurf_bounds(struct metasurface *ms, float xmin, float ymin, float zmin, float xmax, float ymax, float zmax);
    4.57 +
    4.58 +/* resolution of the 3D evaluation grid, the bigger, the better, the slower
    4.59 + * (default: 40, 40, 40)
    4.60 + */
    4.61 +void msurf_resolution(struct metasurface *ms, int xres, int yres, int zres);
    4.62 +
    4.63 +/* isosurface threshold value (default: 0) */
    4.64 +void msurf_threshold(struct metasurface *ms, float thres);
    4.65 +
    4.66 +
    4.67 +/* finally call this to perform the polygonization */
    4.68 +int msurf_polygonize(struct metasurface *ms);
    4.69 +
    4.70 +
    4.71 +#ifdef __cplusplus
    4.72 +}
    4.73 +#endif
    4.74 +
    4.75 +#endif	/* METASURF_H_ */
     5.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     5.2 +++ b/src/mballs.cc	Mon Feb 18 03:46:52 2013 +0200
     5.3 @@ -0,0 +1,140 @@
     5.4 +#include <vector>
     5.5 +#include "opengl.h"
     5.6 +#include "mballs.h"
     5.7 +#include "metasurf.h"
     5.8 +#include "vmath/vmath.h"
     5.9 +
    5.10 +struct MetaBall {
    5.11 +	Vector3 pos;
    5.12 +	float orbit;
    5.13 +	float energy;
    5.14 +	float phase_offs;
    5.15 +};
    5.16 +
    5.17 +#define VOL_SZ			2
    5.18 +#define MBALL_GRID_SZ	50
    5.19 +
    5.20 +static void update();
    5.21 +static float calc_field(float x, float y, float z);
    5.22 +static float eval(float x, float y, float z);
    5.23 +static void vertex(float x, float y, float z);
    5.24 +static void normal(float x, float y, float z);
    5.25 +
    5.26 +static float grid[MBALL_GRID_SZ][MBALL_GRID_SZ][MBALL_GRID_SZ];
    5.27 +static std::vector<MetaBall> balls;
    5.28 +static struct metasurface *msurf;
    5.29 +
    5.30 +bool mball_init()
    5.31 +{
    5.32 +	static const float bbmin = -VOL_SZ / 2.0;
    5.33 +	static const float bbmax = VOL_SZ / 2.0;
    5.34 +
    5.35 +	if(!(msurf = msurf_create())) {
    5.36 +		return false;
    5.37 +	}
    5.38 +	msurf_threshold(msurf, 10);
    5.39 +	msurf_resolution(msurf, MBALL_GRID_SZ, MBALL_GRID_SZ, MBALL_GRID_SZ);
    5.40 +	msurf_bounds(msurf, bbmin, bbmin, bbmin, bbmax, bbmax, bbmax);
    5.41 +	msurf_eval_func(msurf, eval);
    5.42 +	msurf_vertex_func(msurf, vertex);
    5.43 +	//msurf_normal_func(msurf, normal);
    5.44 +
    5.45 +	for(int i=0; i<10; i++) {
    5.46 +		MetaBall mb;
    5.47 +		mb.orbit = 0.25 * rand() / (float)RAND_MAX + 0.35;
    5.48 +		mb.energy = 0.2 * rand() / (float)RAND_MAX + 0.15;
    5.49 +		mb.phase_offs = rand() / (float)RAND_MAX * M_PI * 2.0;
    5.50 +		balls.push_back(mb);
    5.51 +	}
    5.52 +
    5.53 +	return true;
    5.54 +}
    5.55 +
    5.56 +void mball_render()
    5.57 +{
    5.58 +	update();
    5.59 +
    5.60 +	glMatrixMode(GL_MODELVIEW);
    5.61 +	glPushMatrix();
    5.62 +	glScalef(4.0, 4.0, 4.0);
    5.63 +
    5.64 +	glBegin(GL_TRIANGLES);
    5.65 +	msurf_polygonize(msurf);
    5.66 +	glEnd();
    5.67 +
    5.68 +	glPopMatrix();
    5.69 +}
    5.70 +
    5.71 +
    5.72 +static void update()
    5.73 +{
    5.74 +	unsigned int msec = glutGet(GLUT_ELAPSED_TIME);
    5.75 +	float sec = msec / 1000.0;
    5.76 +
    5.77 +	for(size_t i=0; i<balls.size(); i++) {
    5.78 +		float t = sec + balls[i].phase_offs;
    5.79 +		balls[i].pos.x = cos(t * 1.8) * balls[i].orbit;
    5.80 +		balls[i].pos.z = sin(t * 1.2) * balls[i].orbit;
    5.81 +		balls[i].pos.y = (sin(t) + cos(t * 2.0) / 2.0 + sin(t * 3.0) / 3.0) * 0.45;
    5.82 +	}
    5.83 +
    5.84 +	for(int i=0; i<MBALL_GRID_SZ; i++) {
    5.85 +		float x = (float)i / (float)MBALL_GRID_SZ * 2.0 - 1.0;
    5.86 +		for(int j=0; j<MBALL_GRID_SZ; j++) {
    5.87 +			float y = (float)j / (float)MBALL_GRID_SZ * 2.0 - 1.0;
    5.88 +			for(int k=0; k<MBALL_GRID_SZ; k++) {
    5.89 +				float z = (float)k / (float)MBALL_GRID_SZ * 2.0 - 1.0;
    5.90 +				grid[i][j][k] = calc_field(x, y, z);
    5.91 +			}
    5.92 +		}
    5.93 +	}
    5.94 +}
    5.95 +
    5.96 +static float calc_field(float x, float y, float z)
    5.97 +{
    5.98 +	Vector3 pt(x, y, z);
    5.99 +
   5.100 +	float sum = 0.0f;
   5.101 +	for(size_t i=0; i<balls.size(); i++) {
   5.102 +		float dist_sq = (balls[i].pos - pt).length_sq();
   5.103 +		if(dist_sq > 1e-6) {
   5.104 +			sum += balls[i].energy / dist_sq;
   5.105 +		} else {
   5.106 +			sum += 1000.0;
   5.107 +		}
   5.108 +	}
   5.109 +	return sum;
   5.110 +}
   5.111 +
   5.112 +static inline int clamp(int x, int a, int b)
   5.113 +{
   5.114 +	return x < a ? a : (x > b ? b : x);
   5.115 +}
   5.116 +
   5.117 +static float eval(float x, float y, float z)
   5.118 +{
   5.119 +	int cell_x = clamp((int)((x / VOL_SZ + 0.5) * MBALL_GRID_SZ), 0, MBALL_GRID_SZ - 1);
   5.120 +	int cell_y = clamp((int)((y / VOL_SZ + 0.5) * MBALL_GRID_SZ), 0, MBALL_GRID_SZ - 1);
   5.121 +	int cell_z = clamp((int)((z / VOL_SZ + 0.5) * MBALL_GRID_SZ), 0, MBALL_GRID_SZ - 1);
   5.122 +
   5.123 +	return grid[cell_x][cell_y][cell_z];
   5.124 +}
   5.125 +
   5.126 +static void vertex(float x, float y, float z)
   5.127 +{
   5.128 +	float delta = (float)VOL_SZ / (float)MBALL_GRID_SZ;
   5.129 +
   5.130 +	float dfdx = calc_field(x - delta, y, z) - calc_field(x + delta, y, z);
   5.131 +	float dfdy = calc_field(x, y - delta, z) - calc_field(x, y + delta, z);
   5.132 +	float dfdz = calc_field(x, y, z - delta) - calc_field(x, y, z + delta);
   5.133 +
   5.134 +	float len = sqrt(dfdx * dfdx + dfdy * dfdy + dfdz * dfdz);
   5.135 +
   5.136 +	glNormal3f(dfdx / len, dfdy / len, dfdz / len);
   5.137 +	glVertex3f(x, y, z);
   5.138 +}
   5.139 +
   5.140 +static void normal(float x, float y, float z)
   5.141 +{
   5.142 +	glNormal3f(x, y, z);
   5.143 +}
     6.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     6.2 +++ b/src/mballs.h	Mon Feb 18 03:46:52 2013 +0200
     6.3 @@ -0,0 +1,7 @@
     6.4 +#ifndef MBALLS_H_
     6.5 +#define MBALLS_H_
     6.6 +
     6.7 +bool mball_init();
     6.8 +void mball_render();
     6.9 +
    6.10 +#endif	/* MBALLS_H_ */
     7.1 --- a/src/udg.cc	Thu Feb 07 18:52:28 2013 +0200
     7.2 +++ b/src/udg.cc	Mon Feb 18 03:46:52 2013 +0200
     7.3 @@ -6,6 +6,7 @@
     7.4  #include "sdr.h"
     7.5  #include "dither_matrix.h"
     7.6  #include "scroller.h"
     7.7 +#include "mballs.h"
     7.8  
     7.9  #define DITHER_SZ		8
    7.10  #define DITHER_LEVELS	16
    7.11 @@ -35,11 +36,14 @@
    7.12  void destroy_rtarg(struct render_target *rt);
    7.13  
    7.14  int xsz, ysz;
    7.15 -float cam_theta, cam_phi = 25, cam_dist = 8;
    7.16 +float cam_theta, cam_phi = 25, cam_dist = 9;
    7.17  unsigned int dither_tex;
    7.18  struct render_target *rtarg;
    7.19  unsigned int prog;
    7.20  
    7.21 +int opt_highres, opt_regular_render;
    7.22 +
    7.23 +
    7.24  int main(int argc, char **argv)
    7.25  {
    7.26  	glutInit(&argc, argv);
    7.27 @@ -96,10 +100,15 @@
    7.28  		return false;
    7.29  	}
    7.30  
    7.31 +	if(!mball_init()) {
    7.32 +		return false;
    7.33 +	}
    7.34 +
    7.35  	glEnable(GL_CULL_FACE);
    7.36  	glEnable(GL_DEPTH_TEST);
    7.37  	glEnable(GL_LIGHTING);
    7.38  	glEnable(GL_LIGHT0);
    7.39 +	glEnable(GL_NORMALIZE);
    7.40  
    7.41  	return true;
    7.42  }
    7.43 @@ -137,11 +146,15 @@
    7.44  void disp()
    7.45  {
    7.46  	float ldir[] = {-1, 1, 2, 0};
    7.47 +	int xres, yres;
    7.48  
    7.49 -	int xres = xsz / DITHER_SZ;
    7.50 -	int yres = ysz / DITHER_SZ;
    7.51 -	/*int xres = xsz;
    7.52 -	int yres = ysz;*/
    7.53 +	if(opt_highres) {
    7.54 +		xres = xsz;
    7.55 +		yres = ysz;
    7.56 +	} else {
    7.57 +		xres = xsz / DITHER_SZ;
    7.58 +		yres = ysz / DITHER_SZ;
    7.59 +	}
    7.60  
    7.61  	if(!rtarg) {
    7.62  		printf("(re)creating render target (%dx%d)\n", xres, yres);
    7.63 @@ -150,7 +163,9 @@
    7.64  		}
    7.65  	}
    7.66  
    7.67 -	glBindFramebufferEXT(GL_FRAMEBUFFER, rtarg->fbo);
    7.68 +	if(!opt_regular_render) {
    7.69 +		glBindFramebufferEXT(GL_FRAMEBUFFER, rtarg->fbo);
    7.70 +	}
    7.71  	glViewport(0, 0, xres, yres);
    7.72  
    7.73  	glClearColor(1, 1, 1, 1);
    7.74 @@ -161,72 +176,72 @@
    7.75  	glMatrixMode(GL_MODELVIEW);
    7.76  	glLoadIdentity();
    7.77  
    7.78 -	glLightfv(GL_LIGHT0, GL_POSITION, ldir);
    7.79 -
    7.80  	glTranslatef(0, 0, -cam_dist);
    7.81  	glRotatef(cam_phi, 1, 0, 0);
    7.82  	glRotatef(cam_theta, 0, 1, 0);
    7.83  
    7.84 +	glLightfv(GL_LIGHT0, GL_POSITION, ldir);
    7.85 +
    7.86  	const float blue[] = {0.4, 0.45, 1.0, 1};
    7.87  	const float white[] = {1, 1, 1, 1};
    7.88  	glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE, blue);
    7.89  	glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, white);
    7.90  	glMaterialf(GL_FRONT_AND_BACK, GL_SHININESS, 80.0);
    7.91  
    7.92 -	glFrontFace(GL_CW);
    7.93 -	glutSolidTeapot(1.0);
    7.94 -	glFrontFace(GL_CCW);
    7.95 +	mball_render();
    7.96  
    7.97  
    7.98 -	glBindFramebufferEXT(GL_FRAMEBUFFER, 0);
    7.99 -	glViewport(0, 0, xsz, ysz);
   7.100 +	if(!opt_regular_render) {
   7.101 +		glBindFramebufferEXT(GL_FRAMEBUFFER, 0);
   7.102 +		glViewport(0, 0, xsz, ysz);
   7.103  
   7.104 -	glClear(GL_COLOR_BUFFER_BIT);
   7.105 +		glClear(GL_COLOR_BUFFER_BIT);
   7.106  
   7.107 -	glMatrixMode(GL_PROJECTION);
   7.108 -	glPushMatrix();
   7.109 -	glLoadIdentity();
   7.110 -	glMatrixMode(GL_MODELVIEW);
   7.111 -	glLoadIdentity();
   7.112 -	glPushMatrix();
   7.113 +		glMatrixMode(GL_PROJECTION);
   7.114 +		glPushMatrix();
   7.115 +		glLoadIdentity();
   7.116 +		glMatrixMode(GL_MODELVIEW);
   7.117 +		glLoadIdentity();
   7.118 +		glPushMatrix();
   7.119  
   7.120 -	glPushAttrib(GL_ENABLE_BIT);
   7.121 -	glDisable(GL_DEPTH_TEST);
   7.122 +		glPushAttrib(GL_ENABLE_BIT);
   7.123 +		glDisable(GL_DEPTH_TEST);
   7.124  
   7.125 -	bind_program(prog);
   7.126 -	set_uniform_int(prog, "framebuf", 0);
   7.127 -	set_uniform_int(prog, "dither_tex", 1);
   7.128 -	set_uniform_int(prog, "dither_levels", DITHER_LEVELS);
   7.129 -	set_uniform_int(prog, "dither_size", DITHER_SZ);
   7.130 +		bind_program(prog);
   7.131 +		set_uniform_int(prog, "framebuf", 0);
   7.132 +		set_uniform_int(prog, "dither_tex", 1);
   7.133 +		set_uniform_int(prog, "dither_levels", DITHER_LEVELS);
   7.134 +		set_uniform_int(prog, "dither_size", DITHER_SZ);
   7.135  
   7.136 -	glActiveTextureARB(GL_TEXTURE0);
   7.137 -	glBindTexture(GL_TEXTURE_2D, rtarg->color_tex);
   7.138 -	glEnable(GL_TEXTURE_2D);
   7.139 -	glActiveTextureARB(GL_TEXTURE1);
   7.140 -	glBindTexture(GL_TEXTURE_2D, dither_tex);
   7.141 -	glEnable(GL_TEXTURE_2D);
   7.142 +		glActiveTextureARB(GL_TEXTURE0);
   7.143 +		glBindTexture(GL_TEXTURE_2D, rtarg->color_tex);
   7.144 +		glEnable(GL_TEXTURE_2D);
   7.145 +		glActiveTextureARB(GL_TEXTURE1);
   7.146 +		glBindTexture(GL_TEXTURE_2D, dither_tex);
   7.147 +		glEnable(GL_TEXTURE_2D);
   7.148  
   7.149 -	glBegin(GL_QUADS);
   7.150 -	glColor3f(0, 1, 0);
   7.151 -	glTexCoord2f(0, 0); glVertex2f(-1, -1);
   7.152 -	glTexCoord2f(1, 0); glVertex2f(1, -1);
   7.153 -	glTexCoord2f(1, 1); glVertex2f(1, 1);
   7.154 -	glTexCoord2f(0, 1); glVertex2f(-1, 1);
   7.155 -	glEnd();
   7.156 +		glBegin(GL_QUADS);
   7.157 +		glColor3f(0, 1, 0);
   7.158 +		glTexCoord2f(0, 0); glVertex2f(-1, -1);
   7.159 +		glTexCoord2f(1, 0); glVertex2f(1, -1);
   7.160 +		glTexCoord2f(1, 1); glVertex2f(1, 1);
   7.161 +		glTexCoord2f(0, 1); glVertex2f(-1, 1);
   7.162 +		glEnd();
   7.163  
   7.164 -	glActiveTextureARB(GL_TEXTURE1);
   7.165 -	glDisable(GL_TEXTURE_2D);
   7.166 -	glActiveTextureARB(GL_TEXTURE0);
   7.167 -	glDisable(GL_TEXTURE_2D);
   7.168 +		glActiveTextureARB(GL_TEXTURE1);
   7.169 +		glDisable(GL_TEXTURE_2D);
   7.170 +		glActiveTextureARB(GL_TEXTURE0);
   7.171 +		glDisable(GL_TEXTURE_2D);
   7.172  
   7.173 -	bind_program(0);
   7.174 +		bind_program(0);
   7.175  
   7.176 -	glPopAttrib();
   7.177 +		glPopAttrib();
   7.178  
   7.179 -	glMatrixMode(GL_PROJECTION);
   7.180 -	glPopMatrix();
   7.181 -	glMatrixMode(GL_MODELVIEW);
   7.182 -	glPopMatrix();
   7.183 +		glMatrixMode(GL_PROJECTION);
   7.184 +		glPopMatrix();
   7.185 +		glMatrixMode(GL_MODELVIEW);
   7.186 +		glPopMatrix();
   7.187 +	}
   7.188  
   7.189  	glutSwapBuffers();
   7.190  	assert(glGetError() == GL_NO_ERROR);
   7.191 @@ -274,6 +289,18 @@
   7.192  			}
   7.193  		}
   7.194  		break;
   7.195 +
   7.196 +	case 'r':
   7.197 +		opt_regular_render = !opt_regular_render;
   7.198 +		break;
   7.199 +
   7.200 +	case 'h':
   7.201 +		opt_highres = !opt_highres;
   7.202 +		if(rtarg) {
   7.203 +			destroy_rtarg(rtarg);
   7.204 +			rtarg = 0;
   7.205 +		}
   7.206 +		break;
   7.207  	}
   7.208  }
   7.209