home *** CD-ROM | disk | FTP | other *** search
- /* Segment file i/o */
-
- /* Written by Bernie Roehl, March 1992 */
-
- /* The format of a segment file is simple, and very C-like. Each segment
- is bounded by { and }, and contains any combination of attributes and
- additional segments (which are children of the segment they appear in).
- */
-
- #include <stdio.h>
- #include <ctype.h>
- #include <string.h>
- #include "rend386.h"
- #include "plg.h"
-
- int readseg_err = 0;
-
- #define match(a, b) (!strnicmp((a), (b), strlen(b)))
-
- static OBJLIST *curr_objlist = NULL;
-
- static char *boundstypes[] = { "NONE", "SPHERE", "BOX", "CSG", NULL };
-
- void set_readseg_objlist(OBJLIST *olist)
- {
- curr_objlist = olist;
- }
-
- static process_attribute(char *buff, SEGMENT *seg)
- {
- char filename[100];
- float sx = 1, sy = 1, sz = 1;
- long tx = 0, ty = 0, tz = 0;
- FILE *in;
- while (isspace(*buff)) ++buff;
- if (match(buff, "plgfile")) {
- OBJECT *obj;
- sscanf(buff, "plgfile = %s scale %f,%f,%f shift %ld,%ld,%ld", filename, &sx, &sy, &sz, &tx, &ty, &tz);
- set_loadplg_scale(sx, sy, sz);
- set_loadplg_offset(tx, ty, tz);
- seg_set_load_info(seg, filename, sx, sy, sz, tx, ty, tz);
- if ((in = fopen(filename, "r")) == NULL) {
- readseg_err = -1;
- return -1;
- }
- if ((obj = load_plg(in)) == NULL) {
- readseg_err = -2;
- fclose(in);
- return -2;
- }
- seg_setrep(seg, obj);
- set_object_owner(obj, seg);
- if (curr_objlist) add_to_objlist(curr_objlist, obj);
- fclose(in);
- return 0;
- }
- else if (match(buff, "pos")) {
- long tx, ty, tz;
- sscanf(buff, "pos = %ld,%ld,%ld", &tx, &ty, &tz);
- abs_move_segment(seg, tx, ty, tz);
- }
- else if (match(buff, "rot")) {
- float rx, ry, rz;
- sscanf(buff, "rot = %f,%f,%f", &rx, &ry, &rz);
- abs_rot_segment(seg, (long) (rx * 65536L), (long) (ry * 65536L), (long) (rz * 65536L));
- }
- else if (match(buff, "name")) {
- char *p;
- if ((p = strchr(buff, '=')) == NULL) {
- readseg_err = -3;
- return -3;
- }
- do ++p; while (isspace(*p));
- seg_setname(p);
- }
- else if (match(buff, "boundstype")) {
- char *p;
- int i;
- if ((p = strchr(buff, '=')) == NULL) {
- readseg_err = -3;
- return -3;
- }
- do ++p; while (isspace(*p));
- for (i = 0; boundstypes[i]; ++i)
- if (match(p, boundstypes[i]))
- break;
- if (boundstypes[i] == NULL) i = 0;
- set_seg_boundtype(seg, (unsigned char) i);
- }
- else if (match(buff, "boundsorig")) {
- long x = 0, y = 0, z = 0;
- sscanf(buff, "boundsorig = %ld,%ld,%ld", &x, &y, &z);
- set_seg_boundorig(seg, x, y, z);
- }
- else if (match(buff, "boundslimits")) {
- long x = 0, y = 0, z = 0;
- sscanf(buff, "boundslimits = %ld,%ld,%ld", &x, &y, &z);
- set_seg_boundlimits(seg, x, y, z);
- }
- else if (match(buff, "hotspot")) {
- long x = 0, y = 0, z = 0;
- sscanf(buff, "hotspot = %ld,%ld,%ld", &x, &y, &z);
- add_hotspot(seg, x, y, z);
- }
- /* ignore anything we don't understand */
- return 0;
- }
-
- SEGMENT *readseg(FILE *in, SEGMENT *parent)
- {
- SEGMENT *seg;
- char buff[256];
- int c, i = 0;
- if ((seg = new_seg(parent)) == NULL) return NULL;
- while ((c = getc(in)) != EOF) {
- switch (c) {
- case '{':
- readseg(in, seg);
- break;
- case '}':
- return seg;
- case ';':
- buff[i] = '\0';
- process_attribute(buff, seg);
- i = 0;
- break;
- default:
- if (i < sizeof(buff)-1) buff[i++] = c;
- break;
- }
- }
- return seg;
- }
-
- writeseg(FILE *out, SEGMENT *s, int level)
- {
- SEGMENT *p;
- void *q;
- long tx, ty, tz, rx, ry, rz;
- float frx, fry, frz;
- char *name;
- unsigned char btype;
- int i;
- for (i = 0; i < level; ++i) fprintf(out, "\t");
- fprintf(out, "{\n");
- if ((name = seg_getname(s)) != NULL) {
- for (i = 0; i < level; ++i) fprintf(out, "\t");
- fprintf(out, "name = %s;\n", name);
- }
- seg_getposition(s, &tx, &ty, &tz, &rx, &ry, &rz);
- for (i = 0; i < level; ++i) fprintf(out, "\t");
- fprintf(out, "pos = %ld,%ld,%ld;\n", tx, ty, tz);
- for (i = 0; i < level; ++i) fprintf(out, "\t");
- fprintf(out, "rot = %f,%f,%f;\n", ((float) rx) / 65536L, ((float) ry) / 65536L, ((float) rz) / 65536L);
- btype = get_seg_boundinfo(s, &tx, &ty, &tz, &rx, &ry, &rz);
- if (btype) {
- for (i = 0; i < level; ++i) fprintf(out, "\t");
- fprintf(out, "boundstype = %s;\n", boundstypes[btype]);
- for (i = 0; i < level; ++i) fprintf(out, "\t");
- fprintf(out, "boundsorig = %ld,%ld,%ld;\n", tx, ty, tz);
- for (i = 0; i < level; ++i) fprintf(out, "\t");
- fprintf(out, "boundslimits = %ld,%ld,%ld;\n", rx, ry, rz);
- }
- for (q = first_hotspot(s, &tx, &ty, &tz); q; q = next_hotspot(q, &tx, &ty, &tz)) {
- for (i = 0; i < level; ++i) fprintf(out, "\t");
- fprintf(out, "hotspot = %ld,%ld,%ld;\n", tx, ty, tz);
- }
- for (p = child_segment(s); p; p = sibling_segment(p))
- writeseg(out, p, level+1);
- name = seg_get_load_info(s, &frx, &fry, &frz, &tx, &ty, &tz);
- for (i = 0; i < level; ++i) fprintf(out, "\t");
- fprintf(out, "plgfile = %s scale %f,%f,%f shift %ld,%ld,%ld;\n", name, frx, fry, frz, tx, ty, tz);
- for (i = 0; i < level; ++i) fprintf(out, "\t");
- fprintf(out, "}\n");
- return 0;
- }
-