X-Git-Url: https://git.xonotic.org/?a=blobdiff_plain;f=model_alias.c;h=6feaa127b27e316a28640b306cd5b1481f42b22a;hb=7d126079d187081b94c272130fa8d91d2f872483;hp=960de7ae644ea9cd4d7fd2c89fe7581f1971cec0;hpb=7a96ec58916ceea50684acf4c00eaef551199fef;p=xonotic%2Fdarkplaces.git diff --git a/model_alias.c b/model_alias.c index 960de7ae..6feaa127 100644 --- a/model_alias.c +++ b/model_alias.c @@ -28,6 +28,7 @@ cvar_t r_skeletal_debugbonevalue = {0, "r_skeletal_debugbonevalue", "100", "deve cvar_t r_skeletal_debugtranslatex = {0, "r_skeletal_debugtranslatex", "1", "development cvar for testing skeletal model code"}; cvar_t r_skeletal_debugtranslatey = {0, "r_skeletal_debugtranslatey", "1", "development cvar for testing skeletal model code"}; cvar_t r_skeletal_debugtranslatez = {0, "r_skeletal_debugtranslatez", "1", "development cvar for testing skeletal model code"}; +cvar_t mod_alias_supporttagscale = {0, "mod_alias_supporttagscale", "1", "support scaling factors in bone/tag attachment matrices as supported by MD3"}; float mod_md3_sin[320]; @@ -40,6 +41,7 @@ void Mod_AliasInit (void) Cvar_RegisterVariable(&r_skeletal_debugtranslatex); Cvar_RegisterVariable(&r_skeletal_debugtranslatey); Cvar_RegisterVariable(&r_skeletal_debugtranslatez); + Cvar_RegisterVariable(&mod_alias_supporttagscale); for (i = 0;i < 320;i++) mod_md3_sin[i] = sin(i * M_PI * 2.0f / 256.0); } @@ -49,20 +51,32 @@ void Mod_Skeletal_AnimateVertices(const dp_model_t *model, const frameblend_t *f #define MAX_BONES 256 // vertex weighted skeletal int i, k; + int blends; + float desiredscale[3]; float boneposerelative[MAX_BONES][12]; + float *matrix, m[12], bonepose[MAX_BONES][12]; + // interpolate matrices and concatenate them to their parents for (i = 0;i < model->num_bones;i++) { - int blends; - float *matrix, m[12], bonepose[MAX_BONES][12]; for (k = 0;k < 12;k++) m[k] = 0; + VectorClear(desiredscale); for (blends = 0;blends < 4 && frameblend[blends].lerp > 0;blends++) { matrix = model->data_poses + (frameblend[blends].frame * model->num_bones + i) * 12; for (k = 0;k < 12;k++) m[k] += matrix[k] * frameblend[blends].lerp; + desiredscale[0] += frameblend[blends].lerp * VectorLength(matrix ); + desiredscale[1] += frameblend[blends].lerp * VectorLength(matrix + 4); + desiredscale[2] += frameblend[blends].lerp * VectorLength(matrix + 8); } + VectorNormalize(m ); + VectorNormalize(m + 4); + VectorNormalize(m + 8); + VectorScale(m , desiredscale[0], m ); + VectorScale(m + 4, desiredscale[1], m + 4); + VectorScale(m + 8, desiredscale[2], m + 8); if (i == r_skeletal_debugbone.integer) m[r_skeletal_debugbonecomponent.integer % 12] += r_skeletal_debugbonevalue.value; m[3] *= r_skeletal_debugtranslatex.value; @@ -422,9 +436,48 @@ int Mod_Alias_GetTagMatrix(const dp_model_t *model, int poseframe, int tagindex, return 6; Matrix4x4_FromArray12FloatGL(outmatrix, model->data_tags[poseframe * model->num_tags + tagindex].matrixgl); } + + if(!mod_alias_supporttagscale.integer) + Matrix4x4_Normalize3(outmatrix, outmatrix); + return 0; } +int Mod_Alias_GetExtendedTagInfoForIndex(const dp_model_t *model, unsigned int skin, int poseframe, int tagindex, int *parentindex, const char **tagname, matrix4x4_t *tag_localmatrix) +{ + const float *boneframe; + + if(skin >= (unsigned int)model->numskins) + skin = 0; + + if (model->num_bones) + { + if(tagindex >= model->num_bones || tagindex < 0) + return 1; + if (poseframe >= model->num_poses) + return 2; + + boneframe = model->data_poses + poseframe * model->num_bones * 12; + *parentindex = model->data_bones[tagindex].parent; + *tagname = model->data_bones[tagindex].name; + Matrix4x4_FromArray12FloatD3D(tag_localmatrix, boneframe + tagindex * 12); + return 0; + } + + if (model->num_tags) + { + if(tagindex >= model->num_tags || tagindex < 0) + return 1; + if (poseframe >= model->num_tagframes) + return 2; + *tagname = model->data_tags[tagindex].name; + Matrix4x4_FromArray12FloatGL(tag_localmatrix, model->data_tags[poseframe * model->num_tags + tagindex].matrixgl); + return 0; + } + + return 2; +} + int Mod_Alias_GetTagIndexForName(const dp_model_t *model, unsigned int skin, const char *tagname) { int i; @@ -445,7 +498,7 @@ static void Mod_BuildBaseBonePoses(void) { int i, k; double scale; - float *basebonepose = Mem_Alloc(tempmempool, loadmodel->num_bones * sizeof(float[12])); + float *basebonepose = (float *) Mem_Alloc(tempmempool, loadmodel->num_bones * sizeof(float[12])); float *in12f = loadmodel->data_poses; float *out12f = basebonepose; float *outinv12f = loadmodel->data_baseboneposeinverse; @@ -495,7 +548,7 @@ static void Mod_Alias_CalculateBoundingBox(void) frameblend_t frameblend[4]; memset(frameblend, 0, sizeof(frameblend)); frameblend[0].lerp = 1; - vertex3f = Mem_Alloc(loadmodel->mempool, loadmodel->surfmesh.num_vertices * sizeof(float[3])); + vertex3f = (float *) Mem_Alloc(loadmodel->mempool, loadmodel->surfmesh.num_vertices * sizeof(float[3])); VectorClear(loadmodel->normalmins); VectorClear(loadmodel->normalmaxs); yawradius = 0; @@ -742,7 +795,7 @@ static void Mod_BuildAliasSkinFromSkinFrame(texture_t *texture, skinframe_t *ski texture->currentmaterialflags = texture->basematerialflags; } -static void Mod_BuildAliasSkinsFromSkinFiles(texture_t *skin, skinfile_t *skinfile, char *meshname, char *shadername) +static void Mod_BuildAliasSkinsFromSkinFiles(texture_t *skin, skinfile_t *skinfile, const char *meshname, const char *shadername) { int i; skinfileitem_t *skinfileitem; @@ -766,7 +819,7 @@ static void Mod_BuildAliasSkinsFromSkinFiles(texture_t *skin, skinfile_t *skinfi { // don't render unmentioned meshes Mod_BuildAliasSkinFromSkinFrame(skin, NULL); - skin->basematerialflags = skin->currentmaterialflags = 0; + skin->basematerialflags = skin->currentmaterialflags = MATERIALFLAG_NOSHADOW | MATERIALFLAG_NODRAW; } } } @@ -994,12 +1047,12 @@ void Mod_IDP0_Load(dp_model_t *mod, void *buffer, void *bufferend) // load the skins skinfiles = Mod_LoadSkinFiles(); - loadmodel->skinscenes = (animscene_t *)Mem_Alloc(loadmodel->mempool, loadmodel->numskins * sizeof(animscene_t)); - loadmodel->num_textures = loadmodel->num_surfaces * totalskins; - loadmodel->num_texturesperskin = loadmodel->num_surfaces; - loadmodel->data_textures = (texture_t *)Mem_Alloc(loadmodel->mempool, loadmodel->num_surfaces * totalskins * sizeof(texture_t)); if (skinfiles) { + loadmodel->skinscenes = (animscene_t *)Mem_Alloc(loadmodel->mempool, loadmodel->numskins * sizeof(animscene_t)); + loadmodel->num_textures = loadmodel->num_surfaces * loadmodel->numskins; + loadmodel->num_texturesperskin = loadmodel->num_surfaces; + loadmodel->data_textures = (texture_t *)Mem_Alloc(loadmodel->mempool, loadmodel->num_surfaces * loadmodel->numskins * sizeof(texture_t)); Mod_BuildAliasSkinsFromSkinFiles(loadmodel->data_textures, skinfiles, "default", ""); Mod_FreeSkinFiles(skinfiles); for (i = 0;i < loadmodel->numskins;i++) @@ -1012,6 +1065,10 @@ void Mod_IDP0_Load(dp_model_t *mod, void *buffer, void *bufferend) } else { + loadmodel->skinscenes = (animscene_t *)Mem_Alloc(loadmodel->mempool, loadmodel->numskins * sizeof(animscene_t)); + loadmodel->num_textures = loadmodel->num_surfaces * totalskins; + loadmodel->num_texturesperskin = loadmodel->num_surfaces; + loadmodel->data_textures = (texture_t *)Mem_Alloc(loadmodel->mempool, loadmodel->num_surfaces * totalskins * sizeof(texture_t)); totalskins = 0; datapointer = startskins; for (i = 0;i < loadmodel->numskins;i++) @@ -1042,7 +1099,7 @@ void Mod_IDP0_Load(dp_model_t *mod, void *buffer, void *bufferend) } } - sprintf(loadmodel->skinscenes[i].name, "skin %i", i); + dpsnprintf(loadmodel->skinscenes[i].name, sizeof(loadmodel->skinscenes[i].name), "skin %i", i); loadmodel->skinscenes[i].firstframe = totalskins; loadmodel->skinscenes[i].framecount = groupskins; loadmodel->skinscenes[i].framerate = 1.0f / interval; @@ -1051,9 +1108,9 @@ void Mod_IDP0_Load(dp_model_t *mod, void *buffer, void *bufferend) for (j = 0;j < groupskins;j++) { if (groupskins > 1) - sprintf (name, "%s_%i_%i", loadmodel->name, i, j); + dpsnprintf (name, sizeof(name), "%s_%i_%i", loadmodel->name, i, j); else - sprintf (name, "%s_%i", loadmodel->name, i); + dpsnprintf (name, sizeof(name), "%s_%i", loadmodel->name, i); if (!Mod_LoadTextureFromQ3Shader(loadmodel->data_textures + totalskins * loadmodel->num_surfaces, name, false, true, (r_mipskins.integer ? TEXF_MIPMAP : 0) | TEXF_ALPHA | TEXF_PICMIP | TEXF_COMPRESS)) Mod_BuildAliasSkinFromSkinFrame(loadmodel->data_textures + totalskins * loadmodel->num_surfaces, R_SkinFrame_LoadInternalQuake(name, (r_mipskins.integer ? TEXF_MIPMAP : 0) | TEXF_PICMIP, true, r_fullbrights.integer, (unsigned char *)datapointer, skinwidth, skinheight)); datapointer += skinwidth * skinheight; @@ -1928,7 +1985,7 @@ void Mod_DARKPLACESMODEL_Load(dp_model_t *mod, void *buffer, void *bufferend) for (i = 0;i < (int)pheader->num_meshs;i++) { int numverts = BigLong(dpmmesh->num_verts); - meshvertices += numverts;; + meshvertices += numverts; meshtriangles += BigLong(dpmmesh->num_tris); dpmmesh++; } @@ -2159,6 +2216,7 @@ void Mod_PSKMODEL_Load(dp_model_t *mod, void *buffer, void *bufferend) pskchunk_t *pchunk; skinfile_t *skinfiles; char animname[MAX_QPATH]; + size_t size; pchunk = (pskchunk_t *)buffer; if (strcmp(pchunk->id, "ACTRHEAD")) @@ -2525,33 +2583,35 @@ void Mod_PSKMODEL_Load(dp_model_t *mod, void *buffer, void *bufferend) loadmodel->nummodelsurfaces = loadmodel->num_surfaces = nummatts; loadmodel->num_textures = loadmodel->num_surfaces * loadmodel->numskins; loadmodel->num_texturesperskin = loadmodel->num_surfaces; + loadmodel->surfmesh.num_vertices = meshvertices; + loadmodel->surfmesh.num_triangles = meshtriangles; // do most allocations as one merged chunk - data = (unsigned char *)Mem_Alloc(loadmodel->mempool, loadmodel->num_surfaces * sizeof(msurface_t) + loadmodel->num_surfaces * sizeof(int) + loadmodel->num_surfaces * loadmodel->numskins * sizeof(texture_t) + meshtriangles * sizeof(int[3]) + (meshvertices <= 65536 ? meshtriangles * sizeof(unsigned short[3]) : 0) + meshtriangles * sizeof(int[3]) + meshvertices * (sizeof(float[14]) + sizeof(int[4]) + sizeof(float[4])) + loadmodel->num_poses * sizeof(float[12]) + loadmodel->num_bones * sizeof(float[12]) + loadmodel->numskins * sizeof(animscene_t) + loadmodel->num_bones * sizeof(aliasbone_t) + loadmodel->numframes * sizeof(animscene_t)); + size = loadmodel->num_surfaces * sizeof(msurface_t) + loadmodel->num_surfaces * sizeof(int) + loadmodel->num_surfaces * loadmodel->numskins * sizeof(texture_t) + loadmodel->surfmesh.num_triangles * sizeof(int[3]) + loadmodel->surfmesh.num_triangles * sizeof(int[3]) + loadmodel->surfmesh.num_vertices * sizeof(float[3]) + loadmodel->surfmesh.num_vertices * sizeof(float[3]) + loadmodel->surfmesh.num_vertices * sizeof(float[3]) + loadmodel->surfmesh.num_vertices * sizeof(float[3]) + loadmodel->surfmesh.num_vertices * sizeof(float[2]) + loadmodel->surfmesh.num_vertices * sizeof(int[4]) + loadmodel->surfmesh.num_vertices * sizeof(float[4]) + /*loadmodel->num_poses * sizeof(float[12]) + */loadmodel->num_bones * sizeof(float[12]) + loadmodel->numskins * sizeof(animscene_t) + loadmodel->num_bones * sizeof(aliasbone_t) + loadmodel->numframes * sizeof(animscene_t) + ((loadmodel->surfmesh.num_vertices <= 65536) ? (loadmodel->surfmesh.num_triangles * sizeof(unsigned short[3])) : 0); + data = (unsigned char *)Mem_Alloc(loadmodel->mempool, size); loadmodel->data_surfaces = (msurface_t *)data;data += loadmodel->num_surfaces * sizeof(msurface_t); loadmodel->surfacelist = (int *)data;data += loadmodel->num_surfaces * sizeof(int); loadmodel->data_textures = (texture_t *)data;data += loadmodel->num_surfaces * loadmodel->numskins * sizeof(texture_t); - loadmodel->surfmesh.num_vertices = meshvertices; - loadmodel->surfmesh.num_triangles = meshtriangles; - loadmodel->surfmesh.data_element3i = (int *)data;data += meshtriangles * sizeof(int[3]); - loadmodel->surfmesh.data_neighbor3i = (int *)data;data += meshtriangles * sizeof(int[3]); - loadmodel->surfmesh.data_vertex3f = (float *)data;data += meshvertices * sizeof(float[3]); - loadmodel->surfmesh.data_svector3f = (float *)data;data += meshvertices * sizeof(float[3]); - loadmodel->surfmesh.data_tvector3f = (float *)data;data += meshvertices * sizeof(float[3]); - loadmodel->surfmesh.data_normal3f = (float *)data;data += meshvertices * sizeof(float[3]); - loadmodel->surfmesh.data_texcoordtexture2f = (float *)data;data += meshvertices * sizeof(float[2]); - loadmodel->surfmesh.data_vertexweightindex4i = (int *)data;data += meshvertices * sizeof(int[4]); - loadmodel->surfmesh.data_vertexweightinfluence4f = (float *)data;data += meshvertices * sizeof(float[4]); - loadmodel->data_poses = (float *)data;data += loadmodel->num_poses * sizeof(float[12]); + loadmodel->surfmesh.data_element3i = (int *)data;data += loadmodel->surfmesh.num_triangles * sizeof(int[3]); + loadmodel->surfmesh.data_neighbor3i = (int *)data;data += loadmodel->surfmesh.num_triangles * sizeof(int[3]); + loadmodel->surfmesh.data_vertex3f = (float *)data;data += loadmodel->surfmesh.num_vertices * sizeof(float[3]); + loadmodel->surfmesh.data_svector3f = (float *)data;data += loadmodel->surfmesh.num_vertices * sizeof(float[3]); + loadmodel->surfmesh.data_tvector3f = (float *)data;data += loadmodel->surfmesh.num_vertices * sizeof(float[3]); + loadmodel->surfmesh.data_normal3f = (float *)data;data += loadmodel->surfmesh.num_vertices * sizeof(float[3]); + loadmodel->surfmesh.data_texcoordtexture2f = (float *)data;data += loadmodel->surfmesh.num_vertices * sizeof(float[2]); + loadmodel->surfmesh.data_vertexweightindex4i = (int *)data;data += loadmodel->surfmesh.num_vertices * sizeof(int[4]); + loadmodel->surfmesh.data_vertexweightinfluence4f = (float *)data;data += loadmodel->surfmesh.num_vertices * sizeof(float[4]); + //loadmodel->data_poses = (float *)data;data += loadmodel->num_poses * sizeof(float[12]); loadmodel->data_baseboneposeinverse = (float *)data;data += loadmodel->num_bones * sizeof(float[12]); loadmodel->skinscenes = (animscene_t *)data;data += loadmodel->numskins * sizeof(animscene_t); loadmodel->data_bones = (aliasbone_t *)data;data += loadmodel->num_bones * sizeof(aliasbone_t); loadmodel->animscenes = (animscene_t *)data;data += loadmodel->numframes * sizeof(animscene_t); - if (meshvertices <= 65536) + if (loadmodel->surfmesh.num_vertices <= 65536) { - loadmodel->surfmesh.data_element3s = (unsigned short *)data;data += meshtriangles * sizeof(unsigned short[3]); + loadmodel->surfmesh.data_element3s = (unsigned short *)data;data += loadmodel->surfmesh.num_triangles * sizeof(unsigned short[3]); for (i = 0;i < loadmodel->surfmesh.num_triangles*3;i++) loadmodel->surfmesh.data_element3s[i] = loadmodel->surfmesh.data_element3i[i]; } + loadmodel->data_poses = (float *) Mem_Alloc(loadmodel->mempool, loadmodel->num_poses * sizeof(float[12])); for (i = 0;i < loadmodel->numskins;i++) {