diff --git a/polymer/eduke32/build/Makefile b/polymer/eduke32/build/Makefile index 3c518002d..6ee120a67 100644 --- a/polymer/eduke32/build/Makefile +++ b/polymer/eduke32/build/Makefile @@ -160,7 +160,7 @@ OURCFLAGS+= $(BUILDCFLAGS) # TARGETS -UTILS=kextract$(EXESUFFIX) kgroup$(EXESUFFIX) transpal$(EXESUFFIX) wad2art$(EXESUFFIX) wad2map$(EXESUFFIX) +UTILS=kextract$(EXESUFFIX) kgroup$(EXESUFFIX) transpal$(EXESUFFIX) wad2art$(EXESUFFIX) wad2map$(EXESUFFIX) md2tool$(EXESUFFIX) # all: $(OBJ)/$(ENGINELIB) $(OBJ)/$(EDITORLIB) utils: $(UTILS) @@ -192,6 +192,8 @@ wad2art$(EXESUFFIX): $(OBJ)/wad2art.$o $(OBJ)/pragmas.$o $(OBJ)/compat.$o $(OBJ) $(CC) -o $@ $^ $(UTILLIBS) wad2map$(EXESUFFIX): $(OBJ)/wad2map.$o $(OBJ)/pragmas.$o $(OBJ)/compat.$o $(OBJ)/nedmalloc.$o $(CC) -o $@ $^ $(UTILLIBS) +md2tool$(EXESUFFIX): $(OBJ)/md2tool.$o $(OBJ)/compat.$o $(OBJ)/nedmalloc.$o + $(CC) -o $@ $^ $(UTILLIBS) generateicon$(EXESUFFIX): $(OBJ)/generateicon.$o $(OBJ)/kplib.$o $(CC) -o $@ $^ $(UTILLIBS) cacheinfo$(EXESUFFIX): $(OBJ)/cacheinfo.$o $(OBJ)/compat.$o $(OBJ)/nedmalloc.$o diff --git a/polymer/eduke32/build/src/mdsprite.c b/polymer/eduke32/build/src/mdsprite.c index cae7977cb..5197cdc08 100644 --- a/polymer/eduke32/build/src/mdsprite.c +++ b/polymer/eduke32/build/src/mdsprite.c @@ -23,6 +23,17 @@ int32_t curextra=MAXTILES; // #define MODEL_POOL_SIZE 20971520 #define model_data_pool (nedpool *) 0 // take it out of the system pool +#define MIN_CACHETIME_PRINT 5 + +static void QuitOnFatalError(const char *msg) +{ + if (msg) + initprintf("%s\n", msg); + uninitengine(); + exit(1); +} + + int32_t addtileP(int32_t model,int32_t tile,int32_t pallet) { UNREFERENCED_PARAMETER(model); @@ -443,7 +454,7 @@ static int32_t daskinloader(int32_t filh, intptr_t *fptr, int32_t *bpl, int32_t memset(pic,0,xsiz*ysiz*sizeof(coltype)); if (kprender(picfil,picfillen,(intptr_t)pic,xsiz*sizeof(coltype),xsiz,ysiz,0,0)) - { Bfree(picfil); Bfree(pic); return -1; } + { Bfree(picfil); Bfree(pic); return -2; } Bfree(picfil); cptr = &britable[gammabrightness ? 0 : curbrightness][0]; @@ -773,14 +784,20 @@ int32_t mdloadskin(md2model_t *m, int32_t number, int32_t pal, int32_t surf) } else { + int32_t ret; + // if (cachefil >= 0) kclose(cachefil); cachefil = -1; // the compressed version will be saved to disk if ((filh = kopen4load(fn, 0)) < 0) return -1; - if (daskinloader(filh,&fptr,&bpl,&xsiz,&ysiz,&osizx,&osizy,&hasalpha,pal,(globalnoeffect)?0:(hictinting[pal].f&HICEFFECTMASK))) + ret=daskinloader(filh,&fptr,&bpl,&xsiz,&ysiz,&osizx,&osizy,&hasalpha,pal,(globalnoeffect)?0:(hictinting[pal].f&HICEFFECTMASK)); + if (ret) { kclose(filh); - OSD_Printf("Failed loading skin file \"%s\"\n", fn); + OSD_Printf("Failed loading skin file \"%s\": error %d\n", fn, ret); + if (ret==-1) + QuitOnFatalError("OUT OF MEMORY in daskinloader!"); + skinfile[0] = 0; return(0); } @@ -863,7 +880,9 @@ int32_t mdloadskin(md2model_t *m, int32_t number, int32_t pal, int32_t surf) if (willprint) { - OSD_Printf("Load skin: p%d-e%d \"%s\"... cached... %d ms\n", pal, (globalnoeffect)?0:(hictinting[pal].f&HICEFFECTMASK), fn, getticks()-startticks); + int32_t etime = getticks()-startticks; + if (etime>=MIN_CACHETIME_PRINT) + OSD_Printf("Load skin: p%d-e%d \"%s\"... cached... %d ms\n", pal, (globalnoeffect)?0:(hictinting[pal].f&HICEFFECTMASK), fn, etime); willprint = 0; } else @@ -871,7 +890,11 @@ int32_t mdloadskin(md2model_t *m, int32_t number, int32_t pal, int32_t surf) } if (willprint) - OSD_Printf("Load skin: p%d-e%d \"%s\"... %d ms\n", pal, (globalnoeffect)?0:(hictinting[pal].f&HICEFFECTMASK), fn, getticks()-startticks); + { + int32_t etime = getticks()-startticks; + if (etime>=MIN_CACHETIME_PRINT) + OSD_Printf("Load skin: p%d-e%d \"%s\"... %d ms\n", pal, (globalnoeffect)?0:(hictinting[pal].f&HICEFFECTMASK), fn, etime); + } return(*texidx); } @@ -1253,11 +1276,7 @@ static md2model_t *md2load(int32_t fil, const char *filnam) m3->maxdepths = Bmalloc(sizeof(float) * s->numtris); if (!m3->indexes || !m3->vindexes || !m3->maxdepths) - { - initprintf("OUT OF MEMORY in md2load!\n"); - uninitengine(); - exit(1); - } + QuitOnFatalError("OUT OF MEMORY in md2load!"); m3->vbos = NULL; @@ -1479,11 +1498,7 @@ static md3model_t *md3load(int32_t fil) m->maxdepths = Bmalloc(sizeof(float) * maxtrispersurf); if (!m->indexes || !m->vindexes || !m->maxdepths) - { - initprintf("OUT OF MEMORY in md3load!\n"); - uninitengine(); - exit(1); - } + QuitOnFatalError("OUT OF MEMORY in md3load!"); m->vbos = NULL; @@ -1681,11 +1696,7 @@ int md3postload_polymer(md3model_t *m) numtris = Bcalloc(s->numverts, sizeof(int)); if (!s->geometry || !numtris) - { - initprintf("OUT OF MEMORY in md3postload_polymer!\n"); - uninitengine(); - exit(1); - } + QuitOnFatalError("OUT OF MEMORY in md3postload_polymer!"); verti = 0; while (verti < (m->head.numframes * s->numverts)) diff --git a/polymer/eduke32/build/src/polymost.c b/polymer/eduke32/build/src/polymost.c index 729cf4bad..e445ce63d 100644 --- a/polymer/eduke32/build/src/polymost.c +++ b/polymer/eduke32/build/src/polymost.c @@ -203,6 +203,9 @@ int32_t r_parallaxskypanning = 0; extern int16_t editstatus; +#define MIN_CACHETIME_PRINT 5 + + static inline int32_t imod(int32_t a, int32_t b) { if (a >= 0) return(a%b); @@ -1654,7 +1657,7 @@ int32_t gloadtile_hi(int32_t dapic,int32_t dapalnum, int32_t facen, hicreplctyp static char *lastfn = NULL; static int32_t lastsize = 0; - int32_t startticks=0, didprint=0; + int32_t startticks=0, willprint=0; if (!hicr) return -1; if (facen > 0) @@ -1724,15 +1727,13 @@ int32_t gloadtile_hi(int32_t dapic,int32_t dapalnum, int32_t facen, hicreplctyp if (lastpic && lastfn && !Bstrcmp(lastfn,fn)) { - OSD_Printf("Load tile %4d: p%d-m%d-e%d", dapic, dapalnum, dameth, effect); - didprint=1; + willprint=1; Bmemcpy(pic, lastpic, xsiz*ysiz*sizeof(coltype)); } else { if (kprender(picfil,picfillen,(intptr_t)pic,xsiz*sizeof(coltype),xsiz,ysiz,0,0)) { Bfree(picfil); Bfree(pic); return -2; } - OSD_Printf("Load tile %4d: p%d-m%d-e%d \"%s\"", dapic, dapalnum, dameth, effect, fn); - didprint=1; + willprint=2; if (hicprecaching) { @@ -1900,17 +1901,25 @@ int32_t gloadtile_hi(int32_t dapic,int32_t dapalnum, int32_t facen, hicreplctyp /// OSD_Printf("Caching \"%s\"\n", fn); writexcache(fn, picfillen+(dapalnum<<8), dameth, effect, &cachead); - if (didprint) + if (willprint) { - OSD_Printf("... cached... %d ms\n", getticks()-startticks); - didprint = 0; + int32_t etime = getticks()-startticks; + if (etime>=MIN_CACHETIME_PRINT) + OSD_Printf("Load tile %4d: p%d-m%d-e%d %s... cached... %d ms\n", dapic, dapalnum, dameth, effect, + willprint==2 ? fn : "", etime); + willprint = 0; } else OSD_Printf("Cached \"%s\"\n", fn); } - if (didprint) - OSD_Printf("... %d ms\n", getticks()-startticks); + if (willprint) + { + int32_t etime = getticks()-startticks; + if (etime>=MIN_CACHETIME_PRINT) + OSD_Printf("Load tile %4d: p%d-m%d-e%d %s... %d ms\n", dapic, dapalnum, dameth, effect, + willprint==2 ? fn : "", etime); + } return 0; } diff --git a/polymer/eduke32/build/src/util/md2tool.c b/polymer/eduke32/build/src/util/md2tool.c new file mode 100644 index 000000000..97999bf7b --- /dev/null +++ b/polymer/eduke32/build/src/util/md2tool.c @@ -0,0 +1,249 @@ + +#include "compat.h" +#include "build.h" +#include "glbuild.h" +#include "mdsprite.h" + +#include +#include + + +static md2head_t head; + + +static void quit(int32_t status) +{ + exit(status); +} + +static md2model_t *md2load(int *fd, const char *filename, int32_t ronly) +{ + md2model_t *m; + int fil; + + fil = Bopen(filename, ronly?BO_RDONLY:BO_RDWR); + if (fil<0) + { + fprintf(stderr, "Couldn't open `%s': %s\n", filename, strerror(errno)); + quit(2); + } + + m = (md2model_t *)Bcalloc(1,sizeof(md2model_t)); if (!m) quit(1); + m->mdnum = 2; m->scale = .01f; + + Bread(fil,(char *)&head,sizeof(md2head_t)); + + head.id = B_LITTLE32(head.id); head.vers = B_LITTLE32(head.vers); + head.skinxsiz = B_LITTLE32(head.skinxsiz); head.skinysiz = B_LITTLE32(head.skinysiz); + head.framebytes = B_LITTLE32(head.framebytes); head.numskins = B_LITTLE32(head.numskins); + head.numverts = B_LITTLE32(head.numverts); head.numuv = B_LITTLE32(head.numuv); + head.numtris = B_LITTLE32(head.numtris); head.numglcmds = B_LITTLE32(head.numglcmds); + head.numframes = B_LITTLE32(head.numframes); head.ofsskins = B_LITTLE32(head.ofsskins); + head.ofsuv = B_LITTLE32(head.ofsuv); head.ofstris = B_LITTLE32(head.ofstris); + head.ofsframes = B_LITTLE32(head.ofsframes); head.ofsglcmds = B_LITTLE32(head.ofsglcmds); + head.ofseof = B_LITTLE32(head.ofseof); + + if ((head.id != 0x32504449) || (head.vers != 8)) + { + fprintf(stderr, "File `%s' is not an md2 file.\n", filename); + quit(3); + } //"IDP2" + + m->numskins = head.numskins; + m->numframes = head.numframes; + m->numverts = head.numverts; + m->numglcmds = head.numglcmds; + m->framebytes = head.framebytes; + + m->frames = (char *)Bmalloc(m->numframes*m->framebytes); if (!m->frames) quit(1); + m->tris = (md2tri_t *)Bmalloc(head.numtris*sizeof(md2tri_t)); if (!m->tris) quit(1); + m->uv = (md2uv_t *)Bmalloc(head.numuv*sizeof(md2uv_t)); if (!m->uv) quit(1); + + Blseek(fil,head.ofsframes,SEEK_SET); + if (Bread(fil,(char *)m->frames,m->numframes*m->framebytes) != m->numframes*m->framebytes) + quit(1); + + Blseek(fil,head.ofstris,SEEK_SET); + if (Bread(fil,(char *)m->tris,head.numtris*sizeof(md2tri_t)) != (int32_t)(head.numtris*sizeof(md2tri_t))) + quit(1); + + Blseek(fil,head.ofsuv,SEEK_SET); + if (Bread(fil,(char *)m->uv,head.numuv*sizeof(md2uv_t)) != (int32_t)(head.numuv*sizeof(md2uv_t))) + quit(1); + +#if B_BIG_ENDIAN != 0 + { + char *f = (char *)m->frames; + int32_t *l,i,j; + md2frame_t *fr; + + for (i = m->numframes-1; i>=0; i--) + { + fr = (md2frame_t *)f; + l = (int32_t *)&fr->mul; + for (j=5; j>=0; j--) l[j] = B_LITTLE32(l[j]); + f += m->framebytes; + } + + for (i = head.numtris-1; i>=0; i--) + { + m->tris[i].v[0] = B_LITTLE16(m->tris[i].v[0]); + m->tris[i].v[1] = B_LITTLE16(m->tris[i].v[1]); + m->tris[i].v[2] = B_LITTLE16(m->tris[i].v[2]); + m->tris[i].u[0] = B_LITTLE16(m->tris[i].u[0]); + m->tris[i].u[1] = B_LITTLE16(m->tris[i].u[1]); + m->tris[i].u[2] = B_LITTLE16(m->tris[i].u[2]); + } + for (i = head.numuv-1; i>=0; i--) + { + m->uv[i].u = B_LITTLE16(m->uv[i].u); + m->uv[i].v = B_LITTLE16(m->uv[i].v); + } + } +#endif + + *fd = fil; + return(m); +} + + +static void usage_and_quit() +{ + fprintf(stderr, + "Usage:\n" + " md2tool .md2: display info about model\n" + " md2tool -minmax ,,:,, .md2:\n" + " modify `scale' and `translate' fields of MD2 (in-place) to produce given bounds\n" + ); + quit(1); +} + +int main(int argc, char **argv) +{ + char *fn=NULL, *cp; + int32_t fd=-1, i, j, slen; + + int32_t doinfo=1; + + // md2 mul[x,y,z], add[x,y,z] + float mx,my,mz, ax,ay,az; + + // desired model bounds + float dminx=0,dminy=0,dminz=0, dmaxx=1,dmaxy=1,dmaxz=1; + + // md2 uint8-coordinate bounds + uint8_t maxv[3]={0,0,0}; + uint8_t minv[3]={255,255,255}; + + md2frame_t *fr; + uint8_t *vp; + + md2model_t *m; + + if (argc<=1) + usage_and_quit(); + + for (i=1; i= argc) + usage_and_quit(); + if (sscanf(argv[i+1], "%f,%f,%f:%f,%f,%f", &dminx,&dminy,&dminz, &dmaxx,&dmaxy,&dmaxz)!=6) + usage_and_quit(); + i++; + } + else + { + fprintf(stderr, "unrecognized option `%s'\n", cp); + quit(2); + } + } + else + fn = cp; + } + + if (!fn) + usage_and_quit(); + + m = md2load(&fd, fn, doinfo); + + fr = (md2frame_t *)m->frames; + mx=fr->mul.x; my=fr->mul.y; mz=fr->mul.z; + ax=fr->add.x; ay=fr->add.y; az=fr->add.z; + + for (i=0, vp=fr->verts->v; inumverts; i++, vp+=sizeof(md2vert_t)) + { + for (j=0; j<3; j++) + { + maxv[j] = max(maxv[j], vp[j]); + minv[j] = min(minv[j], vp[j]); + } + } + + if (doinfo) + { + printf("------ %s ------\n", fn); + printf("numframes: %d\n", m->numframes); + printf("numverts: %d\n", m->numverts); + printf("numtris: %d\n", head.numtris); + printf("\n"); + printf("ofsframes: %x\n", head.ofsframes); + printf("framebytes: %d\n", head.framebytes); +// printf("framebytes: %d, calculated=%d\n", head.framebytes, sizeof(md2frame_t)+(m->numverts-1)*sizeof(md2vert_t)); + printf("\n"); + + printf("mul=%f %f %f\n", mx, my, mz); + printf("add=%f %f %f\n", ax, ay, az); + + printf("min xyz (s+t) = %f %f %f\n", minv[0]*mx+ax, minv[1]*my+ay, minv[2]*mz+az); + printf("max xyz (s+t) = %f %f %f\n", maxv[0]*mx+ax, maxv[1]*my+ay, maxv[2]*mz+az); + + printf("\n"); + } + else + { + if (maxv[0]-minv[0]>0) mx = (dmaxx-dminx)/(maxv[0]-minv[0]); else mx=0; + if (maxv[1]-minv[1]>0) my = (dmaxy-dminy)/(maxv[1]-minv[1]); else my=0; + if (maxv[2]-minv[2]>0) mz = (dmaxz-dminz)/(maxv[2]-minv[2]); else mz=0; + + if (mx==0||my==0||mz==0) + { + fprintf(stderr, "max[x,y,z]-min[x,y,z] must each be grater 0!\n"); + quit(2); + } + + ax = dmaxx-maxv[0]*mx; + ay = dmaxy-maxv[1]*my; + az = dmaxz-maxv[2]*mz; + +#define ISNAN(x) ((x)!=(x)) +#define ISINF(x) ((x!=0)&&(x/2==x)) + + if (ISNAN(mx)||ISNAN(my)||ISNAN(mz)||ISNAN(ax)||ISNAN(ay)||ISNAN(az)|| + ISINF(mx)||ISINF(my)||ISINF(mz)||ISINF(ax)||ISINF(ay)||ISINF(az)) + { + fprintf(stderr, "Calculation resulted in NaN or Inf.\n"); + quit(2); + } + + Blseek(fd,head.ofsframes,SEEK_SET); + if (Bwrite(fd, &mx, sizeof(mx))!=sizeof(mx)) { perror("write"); quit(3); } + if (Bwrite(fd, &my, sizeof(my))!=sizeof(my)) { perror("write"); quit(3); } + if (Bwrite(fd, &mz, sizeof(mz))!=sizeof(mz)) { perror("write"); quit(3); } + if (Bwrite(fd, &ax, sizeof(ax))!=sizeof(ax)) { perror("write"); quit(3); } + if (Bwrite(fd, &ay, sizeof(ay))!=sizeof(ay)) { perror("write"); quit(3); } + if (Bwrite(fd, &az, sizeof(az))!=sizeof(az)) { perror("write"); quit(3); } + Bclose(fd); + + printf("wrote scale and translate of `%s'.\n", fn); + } + + return 0; +}