2 * Copyright (C) 2003 Robert Kooima
4 * NEVERBALL is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published
6 * by the Free Software Foundation; either version 2 of the License,
7 * or (at your option) any later version.
9 * This program is distributed in the hope that it will be useful, but
10 * WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * General Public License for more details.
20 #include "base_config.h"
24 #define MAGIC 0x4c4f53af
27 /*---------------------------------------------------------------------------*/
29 static void sol_load_mtrl(fs_file fin, struct s_mtrl *mp)
31 get_array(fin, mp->d, 4);
32 get_array(fin, mp->a, 4);
33 get_array(fin, mp->s, 4);
34 get_array(fin, mp->e, 4);
35 get_array(fin, mp->h, 1);
36 get_index(fin, &mp->fl);
38 fs_read(mp->f, 1, PATHMAX, fin);
41 static void sol_load_vert(fs_file fin, struct s_vert *vp)
43 get_array(fin, vp->p, 3);
46 static void sol_load_edge(fs_file fin, struct s_edge *ep)
48 get_index(fin, &ep->vi);
49 get_index(fin, &ep->vj);
52 static void sol_load_side(fs_file fin, struct s_side *sp)
54 get_array(fin, sp->n, 3);
55 get_float(fin, &sp->d);
58 static void sol_load_texc(fs_file fin, struct s_texc *tp)
60 get_array(fin, tp->u, 2);
63 static void sol_load_geom(fs_file fin, struct s_geom *gp)
65 get_index(fin, &gp->mi);
66 get_index(fin, &gp->ti);
67 get_index(fin, &gp->si);
68 get_index(fin, &gp->vi);
69 get_index(fin, &gp->tj);
70 get_index(fin, &gp->sj);
71 get_index(fin, &gp->vj);
72 get_index(fin, &gp->tk);
73 get_index(fin, &gp->sk);
74 get_index(fin, &gp->vk);
77 static void sol_load_lump(fs_file fin, struct s_lump *lp)
79 get_index(fin, &lp->fl);
80 get_index(fin, &lp->v0);
81 get_index(fin, &lp->vc);
82 get_index(fin, &lp->e0);
83 get_index(fin, &lp->ec);
84 get_index(fin, &lp->g0);
85 get_index(fin, &lp->gc);
86 get_index(fin, &lp->s0);
87 get_index(fin, &lp->sc);
90 static void sol_load_node(fs_file fin, struct s_node *np)
92 get_index(fin, &np->si);
93 get_index(fin, &np->ni);
94 get_index(fin, &np->nj);
95 get_index(fin, &np->l0);
96 get_index(fin, &np->lc);
99 static void sol_load_path(fs_file fin, struct s_path *pp)
101 get_array(fin, pp->p, 3);
102 get_float(fin, &pp->t);
103 get_index(fin, &pp->pi);
104 get_index(fin, &pp->f);
105 get_index(fin, &pp->s);
108 static void sol_load_body(fs_file fin, struct s_body *bp)
110 get_index(fin, &bp->pi);
111 get_index(fin, &bp->ni);
112 get_index(fin, &bp->l0);
113 get_index(fin, &bp->lc);
114 get_index(fin, &bp->g0);
115 get_index(fin, &bp->gc);
118 static void sol_load_item(fs_file fin, struct s_item *hp)
120 get_array(fin, hp->p, 3);
121 get_index(fin, &hp->t);
122 get_index(fin, &hp->n);
125 static void sol_load_goal(fs_file fin, struct s_goal *zp)
127 get_array(fin, zp->p, 3);
128 get_float(fin, &zp->r);
131 static void sol_load_swch(fs_file fin, struct s_swch *xp)
133 get_array(fin, xp->p, 3);
134 get_float(fin, &xp->r);
135 get_index(fin, &xp->pi);
136 get_float(fin, &xp->t0);
137 get_float(fin, &xp->t);
138 get_index(fin, &xp->f0);
139 get_index(fin, &xp->f);
140 get_index(fin, &xp->i);
143 static void sol_load_bill(fs_file fin, struct s_bill *rp)
145 get_index(fin, &rp->fl);
146 get_index(fin, &rp->mi);
147 get_float(fin, &rp->t);
148 get_float(fin, &rp->d);
149 get_array(fin, rp->w, 3);
150 get_array(fin, rp->h, 3);
151 get_array(fin, rp->rx, 3);
152 get_array(fin, rp->ry, 3);
153 get_array(fin, rp->rz, 3);
154 get_array(fin, rp->p, 3);
157 static void sol_load_jump(fs_file fin, struct s_jump *jp)
159 get_array(fin, jp->p, 3);
160 get_array(fin, jp->q, 3);
161 get_float(fin, &jp->r);
164 static void sol_load_ball(fs_file fin, struct s_ball *bp)
166 get_array(fin, bp->p, 3);
167 get_float(fin, &bp->r);
169 bp->e[0][0] = bp->E[0][0] = 1.0f;
170 bp->e[0][1] = bp->E[0][1] = 0.0f;
171 bp->e[0][2] = bp->E[0][2] = 0.0f;
173 bp->e[1][0] = bp->E[1][0] = 0.0f;
174 bp->e[1][1] = bp->E[1][1] = 1.0f;
175 bp->e[1][2] = bp->E[1][2] = 0.0f;
177 bp->e[2][0] = bp->E[2][0] = 0.0f;
178 bp->e[2][1] = bp->E[2][1] = 0.0f;
179 bp->e[2][2] = bp->E[2][2] = 1.0f;
182 static void sol_load_view(fs_file fin, struct s_view *wp)
184 get_array(fin, wp->p, 3);
185 get_array(fin, wp->q, 3);
188 static void sol_load_dict(fs_file fin, struct s_dict *dp)
190 get_index(fin, &dp->ai);
191 get_index(fin, &dp->aj);
194 static int sol_load_file(fs_file fin, struct s_file *fp)
200 get_index(fin, &magic);
201 get_index(fin, &version);
203 if (magic != MAGIC || version != SOL_VERSION)
206 get_index(fin, &fp->ac);
207 get_index(fin, &fp->dc);
208 get_index(fin, &fp->mc);
209 get_index(fin, &fp->vc);
210 get_index(fin, &fp->ec);
211 get_index(fin, &fp->sc);
212 get_index(fin, &fp->tc);
213 get_index(fin, &fp->gc);
214 get_index(fin, &fp->lc);
215 get_index(fin, &fp->nc);
216 get_index(fin, &fp->pc);
217 get_index(fin, &fp->bc);
218 get_index(fin, &fp->hc);
219 get_index(fin, &fp->zc);
220 get_index(fin, &fp->jc);
221 get_index(fin, &fp->xc);
222 get_index(fin, &fp->rc);
223 get_index(fin, &fp->uc);
224 get_index(fin, &fp->wc);
225 get_index(fin, &fp->ic);
228 fp->av = (char *) calloc(fp->ac, sizeof (char));
230 fp->mv = (struct s_mtrl *) calloc(fp->mc, sizeof (struct s_mtrl));
232 fp->vv = (struct s_vert *) calloc(fp->vc, sizeof (struct s_vert));
234 fp->ev = (struct s_edge *) calloc(fp->ec, sizeof (struct s_edge));
236 fp->sv = (struct s_side *) calloc(fp->sc, sizeof (struct s_side));
238 fp->tv = (struct s_texc *) calloc(fp->tc, sizeof (struct s_texc));
240 fp->gv = (struct s_geom *) calloc(fp->gc, sizeof (struct s_geom));
242 fp->lv = (struct s_lump *) calloc(fp->lc, sizeof (struct s_lump));
244 fp->nv = (struct s_node *) calloc(fp->nc, sizeof (struct s_node));
246 fp->pv = (struct s_path *) calloc(fp->pc, sizeof (struct s_path));
248 fp->bv = (struct s_body *) calloc(fp->bc, sizeof (struct s_body));
250 fp->hv = (struct s_item *) calloc(fp->hc, sizeof (struct s_item));
252 fp->zv = (struct s_goal *) calloc(fp->zc, sizeof (struct s_goal));
254 fp->jv = (struct s_jump *) calloc(fp->jc, sizeof (struct s_jump));
256 fp->xv = (struct s_swch *) calloc(fp->xc, sizeof (struct s_swch));
258 fp->rv = (struct s_bill *) calloc(fp->rc, sizeof (struct s_bill));
260 fp->uv = (struct s_ball *) calloc(fp->uc, sizeof (struct s_ball));
262 fp->wv = (struct s_view *) calloc(fp->wc, sizeof (struct s_view));
264 fp->dv = (struct s_dict *) calloc(fp->dc, sizeof (struct s_dict));
266 fp->iv = (int *) calloc(fp->ic, sizeof (int));
269 fs_read(fp->av, 1, fp->ac, fin);
271 for (i = 0; i < fp->dc; i++) sol_load_dict(fin, fp->dv + i);
272 for (i = 0; i < fp->mc; i++) sol_load_mtrl(fin, fp->mv + i);
273 for (i = 0; i < fp->vc; i++) sol_load_vert(fin, fp->vv + i);
274 for (i = 0; i < fp->ec; i++) sol_load_edge(fin, fp->ev + i);
275 for (i = 0; i < fp->sc; i++) sol_load_side(fin, fp->sv + i);
276 for (i = 0; i < fp->tc; i++) sol_load_texc(fin, fp->tv + i);
277 for (i = 0; i < fp->gc; i++) sol_load_geom(fin, fp->gv + i);
278 for (i = 0; i < fp->lc; i++) sol_load_lump(fin, fp->lv + i);
279 for (i = 0; i < fp->nc; i++) sol_load_node(fin, fp->nv + i);
280 for (i = 0; i < fp->pc; i++) sol_load_path(fin, fp->pv + i);
281 for (i = 0; i < fp->bc; i++) sol_load_body(fin, fp->bv + i);
282 for (i = 0; i < fp->hc; i++) sol_load_item(fin, fp->hv + i);
283 for (i = 0; i < fp->zc; i++) sol_load_goal(fin, fp->zv + i);
284 for (i = 0; i < fp->jc; i++) sol_load_jump(fin, fp->jv + i);
285 for (i = 0; i < fp->xc; i++) sol_load_swch(fin, fp->xv + i);
286 for (i = 0; i < fp->rc; i++) sol_load_bill(fin, fp->rv + i);
287 for (i = 0; i < fp->uc; i++) sol_load_ball(fin, fp->uv + i);
288 for (i = 0; i < fp->wc; i++) sol_load_view(fin, fp->wv + i);
289 for (i = 0; i < fp->ic; i++) get_index(fin, fp->iv + i);
294 static int sol_load_head(fs_file fin, struct s_file *fp)
299 get_index(fin, &magic);
300 get_index(fin, &version);
302 if (magic != MAGIC || version != SOL_VERSION)
305 get_index(fin, &fp->ac);
306 get_index(fin, &fp->dc);
309 get_index(fin, &fp->mc);
310 get_index(fin, &fp->vc);
311 get_index(fin, &fp->ec);
312 get_index(fin, &fp->sc);
313 get_index(fin, &fp->tc);
314 get_index(fin, &fp->gc);
315 get_index(fin, &fp->lc);
316 get_index(fin, &fp->nc);
317 get_index(fin, &fp->pc);
318 get_index(fin, &fp->bc);
319 get_index(fin, &fp->hc);
320 get_index(fin, &fp->zc);
321 get_index(fin, &fp->jc);
322 get_index(fin, &fp->xc);
323 get_index(fin, &fp->rc);
324 get_index(fin, &fp->uc);
325 get_index(fin, &fp->wc);
326 get_index(fin, &fp->ic);
328 fs_seek(fin, 18 * 4, SEEK_CUR);
332 fp->av = (char *) calloc(fp->ac, sizeof (char));
333 fs_read(fp->av, 1, fp->ac, fin);
340 fp->dv = (struct s_dict *) calloc(fp->dc, sizeof (struct s_dict));
342 for (i = 0; i < fp->dc; i++)
343 sol_load_dict(fin, fp->dv + i);
349 int sol_load_only_file(struct s_file *fp, const char *filename)
354 if ((fin = fs_open(filename, "r")))
356 res = sol_load_file(fin, fp);
362 int sol_load_only_head(struct s_file *fp, const char *filename)
367 if ((fin = fs_open(filename, "r")))
369 res = sol_load_head(fin, fp);
375 /*---------------------------------------------------------------------------*/
377 static void sol_stor_mtrl(fs_file fout, struct s_mtrl *mp)
379 put_array(fout, mp->d, 4);
380 put_array(fout, mp->a, 4);
381 put_array(fout, mp->s, 4);
382 put_array(fout, mp->e, 4);
383 put_array(fout, mp->h, 1);
384 put_index(fout, &mp->fl);
386 fs_write(mp->f, 1, PATHMAX, fout);
389 static void sol_stor_vert(fs_file fout, struct s_vert *vp)
391 put_array(fout, vp->p, 3);
394 static void sol_stor_edge(fs_file fout, struct s_edge *ep)
396 put_index(fout, &ep->vi);
397 put_index(fout, &ep->vj);
400 static void sol_stor_side(fs_file fout, struct s_side *sp)
402 put_array(fout, sp->n, 3);
403 put_float(fout, &sp->d);
406 static void sol_stor_texc(fs_file fout, struct s_texc *tp)
408 put_array(fout, tp->u, 2);
411 static void sol_stor_geom(fs_file fout, struct s_geom *gp)
413 put_index(fout, &gp->mi);
414 put_index(fout, &gp->ti);
415 put_index(fout, &gp->si);
416 put_index(fout, &gp->vi);
417 put_index(fout, &gp->tj);
418 put_index(fout, &gp->sj);
419 put_index(fout, &gp->vj);
420 put_index(fout, &gp->tk);
421 put_index(fout, &gp->sk);
422 put_index(fout, &gp->vk);
425 static void sol_stor_lump(fs_file fout, struct s_lump *lp)
427 put_index(fout, &lp->fl);
428 put_index(fout, &lp->v0);
429 put_index(fout, &lp->vc);
430 put_index(fout, &lp->e0);
431 put_index(fout, &lp->ec);
432 put_index(fout, &lp->g0);
433 put_index(fout, &lp->gc);
434 put_index(fout, &lp->s0);
435 put_index(fout, &lp->sc);
438 static void sol_stor_node(fs_file fout, struct s_node *np)
440 put_index(fout, &np->si);
441 put_index(fout, &np->ni);
442 put_index(fout, &np->nj);
443 put_index(fout, &np->l0);
444 put_index(fout, &np->lc);
447 static void sol_stor_path(fs_file fout, struct s_path *pp)
449 put_array(fout, pp->p, 3);
450 put_float(fout, &pp->t);
451 put_index(fout, &pp->pi);
452 put_index(fout, &pp->f);
453 put_index(fout, &pp->s);
456 static void sol_stor_body(fs_file fout, struct s_body *bp)
458 put_index(fout, &bp->pi);
459 put_index(fout, &bp->ni);
460 put_index(fout, &bp->l0);
461 put_index(fout, &bp->lc);
462 put_index(fout, &bp->g0);
463 put_index(fout, &bp->gc);
466 static void sol_stor_item(fs_file fout, struct s_item *hp)
468 put_array(fout, hp->p, 3);
469 put_index(fout, &hp->t);
470 put_index(fout, &hp->n);
473 static void sol_stor_goal(fs_file fout, struct s_goal *zp)
475 put_array(fout, zp->p, 3);
476 put_float(fout, &zp->r);
479 static void sol_stor_swch(fs_file fout, struct s_swch *xp)
481 put_array(fout, xp->p, 3);
482 put_float(fout, &xp->r);
483 put_index(fout, &xp->pi);
484 put_float(fout, &xp->t0);
485 put_float(fout, &xp->t);
486 put_index(fout, &xp->f0);
487 put_index(fout, &xp->f);
488 put_index(fout, &xp->i);
491 static void sol_stor_bill(fs_file fout, struct s_bill *rp)
493 put_index(fout, &rp->fl);
494 put_index(fout, &rp->mi);
495 put_float(fout, &rp->t);
496 put_float(fout, &rp->d);
497 put_array(fout, rp->w, 3);
498 put_array(fout, rp->h, 3);
499 put_array(fout, rp->rx, 3);
500 put_array(fout, rp->ry, 3);
501 put_array(fout, rp->rz, 3);
502 put_array(fout, rp->p, 3);
505 static void sol_stor_jump(fs_file fout, struct s_jump *jp)
507 put_array(fout, jp->p, 3);
508 put_array(fout, jp->q, 3);
509 put_float(fout, &jp->r);
512 static void sol_stor_ball(fs_file fout, struct s_ball *bp)
514 put_array(fout, bp->p, 3);
515 put_float(fout, &bp->r);
518 static void sol_stor_view(fs_file fout, struct s_view *wp)
520 put_array(fout, wp->p, 3);
521 put_array(fout, wp->q, 3);
524 static void sol_stor_dict(fs_file fout, struct s_dict *dp)
526 put_index(fout, &dp->ai);
527 put_index(fout, &dp->aj);
530 static void sol_stor_file(fs_file fout, struct s_file *fp)
534 int version = SOL_VERSION;
536 put_index(fout, &magic);
537 put_index(fout, &version);
539 put_index(fout, &fp->ac);
540 put_index(fout, &fp->dc);
541 put_index(fout, &fp->mc);
542 put_index(fout, &fp->vc);
543 put_index(fout, &fp->ec);
544 put_index(fout, &fp->sc);
545 put_index(fout, &fp->tc);
546 put_index(fout, &fp->gc);
547 put_index(fout, &fp->lc);
548 put_index(fout, &fp->nc);
549 put_index(fout, &fp->pc);
550 put_index(fout, &fp->bc);
551 put_index(fout, &fp->hc);
552 put_index(fout, &fp->zc);
553 put_index(fout, &fp->jc);
554 put_index(fout, &fp->xc);
555 put_index(fout, &fp->rc);
556 put_index(fout, &fp->uc);
557 put_index(fout, &fp->wc);
558 put_index(fout, &fp->ic);
560 fs_write(fp->av, 1, fp->ac, fout);
562 for (i = 0; i < fp->dc; i++) sol_stor_dict(fout, fp->dv + i);
563 for (i = 0; i < fp->mc; i++) sol_stor_mtrl(fout, fp->mv + i);
564 for (i = 0; i < fp->vc; i++) sol_stor_vert(fout, fp->vv + i);
565 for (i = 0; i < fp->ec; i++) sol_stor_edge(fout, fp->ev + i);
566 for (i = 0; i < fp->sc; i++) sol_stor_side(fout, fp->sv + i);
567 for (i = 0; i < fp->tc; i++) sol_stor_texc(fout, fp->tv + i);
568 for (i = 0; i < fp->gc; i++) sol_stor_geom(fout, fp->gv + i);
569 for (i = 0; i < fp->lc; i++) sol_stor_lump(fout, fp->lv + i);
570 for (i = 0; i < fp->nc; i++) sol_stor_node(fout, fp->nv + i);
571 for (i = 0; i < fp->pc; i++) sol_stor_path(fout, fp->pv + i);
572 for (i = 0; i < fp->bc; i++) sol_stor_body(fout, fp->bv + i);
573 for (i = 0; i < fp->hc; i++) sol_stor_item(fout, fp->hv + i);
574 for (i = 0; i < fp->zc; i++) sol_stor_goal(fout, fp->zv + i);
575 for (i = 0; i < fp->jc; i++) sol_stor_jump(fout, fp->jv + i);
576 for (i = 0; i < fp->xc; i++) sol_stor_swch(fout, fp->xv + i);
577 for (i = 0; i < fp->rc; i++) sol_stor_bill(fout, fp->rv + i);
578 for (i = 0; i < fp->uc; i++) sol_stor_ball(fout, fp->uv + i);
579 for (i = 0; i < fp->wc; i++) sol_stor_view(fout, fp->wv + i);
580 for (i = 0; i < fp->ic; i++) put_index(fout, fp->iv + i);
583 /*---------------------------------------------------------------------------*/
585 int sol_stor(struct s_file *fp, const char *filename)
589 if ((fout = fs_open(filename, "w")))
591 sol_stor_file(fout, fp);
599 void sol_free(struct s_file *fp)
601 if (fp->av) free(fp->av);
602 if (fp->mv) free(fp->mv);
603 if (fp->vv) free(fp->vv);
604 if (fp->ev) free(fp->ev);
605 if (fp->sv) free(fp->sv);
606 if (fp->tv) free(fp->tv);
607 if (fp->gv) free(fp->gv);
608 if (fp->lv) free(fp->lv);
609 if (fp->nv) free(fp->nv);
610 if (fp->pv) free(fp->pv);
611 if (fp->bv) free(fp->bv);
612 if (fp->hv) free(fp->hv);
613 if (fp->zv) free(fp->zv);
614 if (fp->jv) free(fp->jv);
615 if (fp->xv) free(fp->xv);
616 if (fp->rv) free(fp->rv);
617 if (fp->uv) free(fp->uv);
618 if (fp->wv) free(fp->wv);
619 if (fp->dv) free(fp->dv);
620 if (fp->iv) free(fp->iv);
622 memset(fp, 0, sizeof (struct s_file));
625 /*---------------------------------------------------------------------------*/