ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/radiance/ray/src/common/readwfobj.c
(Generate patch)

Comparing ray/src/common/readwfobj.c (file contents):
Revision 2.2 by greg, Thu Apr 23 03:19:48 2020 UTC vs.
Revision 2.10 by greg, Tue Feb 7 20:28:16 2023 UTC

# Line 16 | Line 16 | static const char RCSid[] = "$Id$";
16   #include <ctype.h>
17   #include "objutil.h"
18  
19 typedef int     VNDX[3];        /* vertex index (point,map,normal) */
20
19   #define MAXARG          512     /* maximum # arguments in a statement */
20  
21   static int      lineno;         /* current line number */
# Line 115 | Line 113 | syntax(const char *fn, const char *er)
113          error(USER, errmsg);
114   }
115  
118 /* Add a vertex to our scene */
119 static void
120 add_vertex(Scene *sc, double x, double y, double z)
121 {
122        sc->vert = chunk_alloc(Vertex, sc->vert, sc->nverts);
123        sc->vert[sc->nverts].p[0] = x;
124        sc->vert[sc->nverts].p[1] = y;
125        sc->vert[sc->nverts].p[2] = z;
126        sc->vert[sc->nverts++].vflist = NULL;
127 }
128
129 /* Add a texture coordinate to our scene */
130 static void
131 add_texture(Scene *sc, double u, double v)
132 {
133        sc->tex = chunk_alloc(TexCoord, sc->tex, sc->ntex);
134        sc->tex[sc->ntex].u = u;
135        sc->tex[sc->ntex].v = v;
136        sc->ntex++;
137 }
138
139 /* Add a surface normal to our scene */
140 static int
141 add_normal(Scene *sc, double xn, double yn, double zn)
142 {
143        FVECT   nrm;
144
145        nrm[0] = xn; nrm[1] = yn; nrm[2] = zn;
146        if (normalize(nrm) == .0)
147                return(0);
148        sc->norm = chunk_alloc(Normal, sc->norm, sc->nnorms);
149        VCOPY(sc->norm[sc->nnorms], nrm);
150        sc->nnorms++;
151        return(1);
152 }
153
116   /* combine multi-group name into single identifier w/o spaces */
117   static char *
118   group_name(int ac, char **av)
# Line 179 | Line 141 | group_name(int ac, char **av)
141          return(nambuf);
142   }
143  
144 < /* set current group */
183 < static void
184 < set_group(Scene *sc, const char *nm)
185 < {
186 <        sc->lastgrp = findName(nm, (const char **)sc->grpname, sc->ngrps);
187 <        if (sc->lastgrp >= 0)
188 <                return;
189 <        sc->grpname = chunk_alloc(char *, sc->grpname, sc->ngrps);
190 <        sc->grpname[sc->lastgrp=sc->ngrps++] = savqstr((char *)nm);
191 < }
192 <
193 < /* set current material */
194 < static void
195 < set_material(Scene *sc, const char *nm)
196 < {
197 <        sc->lastmat = findName(nm, (const char **)sc->matname, sc->nmats);
198 <        if (sc->lastmat >= 0)
199 <                return;
200 <        sc->matname = chunk_alloc(char *, sc->matname, sc->nmats);
201 <        sc->matname[sc->lastmat=sc->nmats++] = savqstr((char *)nm);
202 < }
203 <
204 < /* Add a new face to scene */
144 > /* add a new face to scene */
145   static int
146   add_face(Scene *sc, const VNDX ondx, int ac, char *av[])
147   {
148 <        Face    *f;
148 >        VNDX    vdef[4];
149 >        VNDX    *varr = vdef;
150 >        Face    *f = NULL;
151          int     i;
152          
153 <        if (ac < 3)
153 >        if (ac < 3)                             /* legal polygon? */
154                  return(0);
155 <        f = (Face *)emalloc(sizeof(Face)+sizeof(VertEnt)*(ac-3));
156 <        f->flags = 0;
157 <        f->nv = ac;
158 <        f->grp = sc->lastgrp;
159 <        f->mat = sc->lastmat;
160 <        for (i = 0; i < ac; i++) {              /* add each vertex */
161 <                VNDX    vin;
162 <                int     j;
163 <                if (!cvtndx(vin, sc, ondx, av[i])) {
164 <                        efree((char *)f);
223 <                        return(0);
224 <                }
225 <                f->v[i].vid = vin[0];
226 <                f->v[i].tid = vin[1];
227 <                f->v[i].nid = vin[2];
228 <                f->v[i].fnext = NULL;
229 <                for (j = i; j-- > 0; )
230 <                        if (f->v[j].vid == vin[0])
231 <                                break;
232 <                if (j < 0) {                    /* first occurrence? */
233 <                        f->v[i].fnext = sc->vert[vin[0]].vflist;
234 <                        sc->vert[vin[0]].vflist = f;
235 <                } else if (ac == 3)             /* degenerate triangle? */
236 <                        f->flags |= FACE_DEGENERATE;
237 <        }
238 <        f->next = sc->flist;                    /* push onto face list */
239 <        sc->flist = f;
240 <        sc->nfaces++;
241 <                                                /* check face area */
242 <        if (!(f->flags & FACE_DEGENERATE) && faceArea(sc, f, NULL) <= FTINY)
243 <                f->flags |= FACE_DEGENERATE;
244 <        return(1);
155 >        if (ac > 4)                             /* need to allocate array? */
156 >                varr = (VNDX *)emalloc(ac*sizeof(VNDX));
157 >        for (i = ac; i--; )                     /* index each vertex */
158 >                if (!cvtndx(varr[i], sc, ondx, av[i]))
159 >                        break;
160 >        if (i < 0)                              /* create face if indices OK */
161 >                f = addFace(sc, varr, ac);
162 >        if (varr != vdef)
163 >                efree(varr);
164 >        return(f != NULL);
165   }
166  
167   /* Load a .OBJ file */
# Line 251 | Line 171 | loadOBJ(Scene *sc, const char *fspec)
171          FILE    *fp;
172          char    *argv[MAXARG];
173          int     argc;
174 <        char    buf[256];
174 >        char    buf[1024];
175          int     nstats=0, nunknown=0;
176          int     onfaces;
177          VNDX    ondx;
# Line 272 | Line 192 | loadOBJ(Scene *sc, const char *fspec)
192                  error(SYSTEM, errmsg);
193                  return(NULL);
194          }
195 + #ifdef getc_unlocked                    /* avoid stupid semaphores */
196 +        flockfile(fp);
197 + #endif
198          if (sc == NULL)
199                  sc = newScene();
200          lineno = 0;
# Line 288 | Line 211 | loadOBJ(Scene *sc, const char *fspec)
211                                          syntax(fspec, "bad vertex");
212                                          goto failure;
213                                  }
214 <                                add_vertex(sc, atof(argv[1]),
214 >                                addVertex(sc, atof(argv[1]),
215                                                  atof(argv[2]),
216                                                  atof(argv[3]));
217                                  break;
# Line 297 | Line 220 | loadOBJ(Scene *sc, const char *fspec)
220                                          goto unknown;
221                                  if (badarg(argc-1,argv+1,"ff"))
222                                          goto unknown;
223 <                                add_texture(sc, atof(argv[1]), atof(argv[2]));
223 >                                addTexture(sc, atof(argv[1]), atof(argv[2]));
224                                  break;
225                          case 'n':                       /* normal */
226                                  if (argv[0][2])
# Line 306 | Line 229 | loadOBJ(Scene *sc, const char *fspec)
229                                          syntax(fspec, "bad normal");
230                                          goto failure;
231                                  }
232 <                                if (!add_normal(sc, atof(argv[1]),
232 >                                if (addNormal(sc, atof(argv[1]),
233                                                  atof(argv[2]),
234 <                                                atof(argv[3]))) {
234 >                                                atof(argv[3])) < 0) {
235                                          syntax(fspec, "zero normal");
236                                          goto failure;
237                                  }
# Line 334 | Line 257 | loadOBJ(Scene *sc, const char *fspec)
257                                  syntax(fspec, "bad # arguments");
258                                  goto failure;
259                          }
260 <                        set_material(sc, argv[1]);
260 >                        setMaterial(sc, argv[1]);
261                          break;
262                  case 'o':               /* object name */
263                  case 'g':               /* group name */
# Line 342 | Line 265 | loadOBJ(Scene *sc, const char *fspec)
265                                  syntax(fspec, "missing argument");
266                                  goto failure;
267                          }
268 <                        set_group(sc, group_name(argc-1, argv+1));
268 >                        setGroup(sc, group_name(argc-1, argv+1));
269                          break;
270                  case '#':               /* comment */
271                          continue;
# Line 356 | Line 279 | loadOBJ(Scene *sc, const char *fspec)
279                          fprintf(stderr, " %8d statements\r", nstats);
280          }
281   #if POPEN_SUPPORT
282 <        if (fspec[0] == '!')
283 <                pclose(fp);
284 <        else
282 >        if (fspec[0] == '!') {
283 >                if (pclose(fp) != 0) {
284 >                        sprintf(errmsg, "Bad return status from: %s", fspec+1);
285 >                        error(USER, errmsg);
286 >                        freeScene(sc);
287 >                        return(NULL);
288 >                }
289 >        } else
290   #endif
291          if (fp != stdin)
292                  fclose(fp);
293 <        sprintf(buf, "%d statements read from \"%s\"", nstats, fspec);
293 > #ifdef getc_unlocked
294 >        else
295 >                funlockfile(fp);
296 > #endif
297 >        if (verbose)
298 >                fprintf(stderr, "Read %d statements\n", nstats);
299 >        if (strlen(fspec) < sizeof(buf)-32)
300 >                sprintf(buf, "%d statements read from \"%s\"", nstats, fspec);
301 >        else
302 >                sprintf(buf, "%d statements read from (TOO LONG TO SHOW)", nstats);
303          addComment(sc, buf);
304          if (nunknown) {
305                  sprintf(buf, "\t%d unrecognized", nunknown);

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines