/* MotionManager::startMotion start a motion */
bool MotionManager::startMotion(VMD * vmd, const char *name, bool full, bool once, bool enableSmooth, bool enableRePos, float priority)
{
   MotionPlayer *m, *tmp1, *tmp2;

   if (vmd == NULL || name == NULL) return false;

   /* purge inactive motion managers */
   purgeMotion();

   /* allocate new motion */
   m = new MotionPlayer;
   MotionPlayer_initialize(m);

   m->name = MMDFiles_strdup(name);
   m->priority = priority;
   m->onEnd = once ? 2 : 1; /* if loop is not specified, this motion will be deleted */
   m->ignoreStatic = full ? false : true;
   m->enableSmooth = enableSmooth;
   m->enableRePos = enableRePos;

   startMotionSub(vmd, m);

   /* set reset timer for bones/faces that are not controlled by the given base motion */
   if (!m->ignoreStatic)
      m_beginningNonControlledBlend = 10.0f;

   /* add this new motion to the last of the motion player list, consulting priority */
   if (m_playerList == NULL || m_playerList->priority > m->priority) {
      m->next = m_playerList;
      m_playerList = m;
   } else {
      tmp2 = m_playerList->next; /* skip the base motion */
      tmp1 = m_playerList;
      while (tmp2) {
         if (tmp2->priority > m->priority) {
            /* insert here */
            m->next = tmp2;
            tmp1->next = m;
            break;
         }
         tmp1 = tmp2;
         tmp2 = tmp2->next;
      }
      if (!tmp2) { /* append */
         m->next = NULL;
         tmp1->next = m;
      }
   }

   return true;
}
Beispiel #2
0
/* PMDFace::setup: initialize and setup face */
void PMDFace::setup(PMDFile_Face *face, PMDFile_Face_Vertex *faceVertexList)
{
   unsigned long i;
   char name[21];

   clear();

   /* name */
   strncpy(name, face->name, 20);
   name[20] = '\0';
   m_name = MMDFiles_strdup(name);

   /* type */
   m_type = face->type;

   /* number of vertices */
   m_numVertex = face->numVertex;

   if (m_numVertex) {
      /* vertex list */
      m_vertex = (PMDFaceVertex *) malloc(sizeof(PMDFaceVertex) * m_numVertex);
      for (i = 0; i < m_numVertex; i++) {
         m_vertex[i].id = faceVertexList[i].vertexID;
         if (m_vertex[i].id >= PMDFACE_MAXVERTEXID) /* a workaround for some models with corrupted face index values */
            m_vertex[i].id -= PMDFACE_MAXVERTEXID;
         m_vertex[i].pos.setValue(faceVertexList[i].pos[0], faceVertexList[i].pos[1], faceVertexList[i].pos[2]);
      }
   }

#ifdef MMDFILES_CONVERTCOORDINATESYSTEM
   /* left-handed system: PMD, DirectX */
   /* right-handed system: OpenGL, bulletphysics */
   /* reverse Z value on vertices */
   for (i = 0; i < m_numVertex; i++) {
      m_vertex[i].pos.setZ(- m_vertex[i].pos.z());
   }
#endif /* MMDFILES_CONVERTCOORDINATESYSTEM */
}
/* MMDFiles_basename: get file name from path */
char *MMDFiles_basename(const char *file)
{
   int i, len, index = -1;
   char size;
   char *base;

   len = MMDFiles_strlen(file);

   for(i = 0; i < len; i += size) {
      size = MMDFiles_getcharsize(&file[i]);
      if(size == 1 && MMDFiles_dirseparator(file[i]) == true)
         index = i;
   }

   if(index >= 0) {
      base = (char *) malloc(sizeof(char) * (len - index));
      strncpy(base, &file[index + 1], len - index - 1);
      base[len - index - 1] = '\0';
   } else {
      base = MMDFiles_strdup(file);
   }

   return base;
}
/* MMDFiles_dirname: get directory name from path */
char *MMDFiles_dirname(const char *file)
{
   int i, len, index = -1;
   char size;
   char *dir;

   len = MMDFiles_strlen(file);

   for(i = 0; i < len; i += size) {
      size = MMDFiles_getcharsize(&file[i]);
      if(size == 1 && MMDFiles_dirseparator(file[i]) == true)
         index = i;
   }

   if(index >= 0) {
      dir = (char *) malloc(sizeof(char *) * (index + 1));
      strncpy(dir, file, index);
      dir[index] = '\0';
   } else {
      dir = MMDFiles_strdup(".");
   }

   return dir;
}
Beispiel #5
0
/* MMDAgent_strdup: strdup */
char *MMDAgent_strdup(const char *str)
{
    return MMDFiles_strdup(str);
}
Beispiel #6
0
/* PMDBone::setup: initialize and setup bone */
bool PMDBone::setup(PMDFile_Bone *b, PMDBone *boneList, unsigned short maxBones, PMDBone *rootBone)
{
   bool ret = true;
   char name[21];

   clear();

   /* name */
   strncpy(name, b->name, 20);
   name[20] = '\0';
   m_name = MMDFiles_strdup(name);

   /* mark if this bone should be treated as angle-constrained bone in IK process */
   if (strstr(m_name, PMDBONE_KNEENAME))
      m_limitAngleX = true;
   else
      m_limitAngleX = false;

   /* parent bone */
   if (b->parentBoneID != -1) {
      /* has parent bone */
      if (b->parentBoneID >= maxBones) {
         ret = false;
      } else {
         m_parentBone = &(boneList[b->parentBoneID]);
         m_parentIsRoot = false;
      }
   } else {
      /* no parent bone */
      if (rootBone) {
         /* set model root bone as parent */
         m_parentBone = rootBone;
         m_parentIsRoot = true;
      } else {
         /* no parent, just use it */
         m_parentIsRoot = false;
      }
   }

   /* child bone */
   if (b->childBoneID != -1) {
      if (b->childBoneID >= maxBones)
         ret = false;
      else
         m_childBone = &(boneList[b->childBoneID]);
   }

   /* type */
   m_type = b->type;

   /* target bone to which this bone is subject to */
   if (m_type == UNDER_IK || m_type == UNDER_ROTATE) {
      m_targetBone = &(boneList[b->targetBoneID]);
      if (b->targetBoneID >= maxBones)
         ret = false;
      else
         m_targetBone = &(boneList[b->targetBoneID]);
   }

   /* store the value of targetBoneID as co-rotate coef if kind == FOLLOW_ROTATE */
   if (m_type == FOLLOW_ROTATE)
      m_rotateCoef = (float) b->targetBoneID * 0.01f;

   /* store absolute bone positions */
   /* reverse Z value on bone position */
#ifdef MMDFILES_CONVERTCOORDINATESYSTEM
   m_originPosition = btVector3(b->pos[0], b->pos[1], -b->pos[2]);
#else
   m_originPosition = btVector3(b->pos[0], b->pos[1], b->pos[2]);
#endif /* MMDFILES_CONVERTCOORDINATESYSTEM */

   /* reset current transform values */
   m_trans.setOrigin(m_originPosition);

   /* set absolute position->origin transform matrix for skinning */
   m_transMoveToOrigin.setOrigin(-m_originPosition);

   return ret;
}
/* MMDFiles_pathdup: convert charset from application to system */
char *MMDFiles_pathdup(const char *str)
{
#ifdef _WIN32
   return MMDFiles_strdup(str);
#endif /* _WIN32 */
#ifdef __APPLE__
   size_t i, size;
   char *inBuff, *outBuff;
   size_t inLen, outLen;
   CFStringRef cfs;

   inLen = MMDFiles_strlen(str);
   if(inLen <= 0)
      return NULL;

   inBuff = MMDFiles_strdup(str);
   if(inBuff == NULL)
      return NULL;

   /* convert directory separator */
   for(i = 0; i < inLen; i += size) {
      size = MMDFiles_getcharsize(&inBuff[i]);
      if(size == 1 && MMDFiles_dirseparator(inBuff[i]) == true)
         inBuff[i] = MMDFILES_DIRSEPARATOR;
   }

   /* convert multi-byte char */
   cfs = CFStringCreateWithCString(NULL, inBuff, kCFStringEncodingDOSJapanese);
   outLen = CFStringGetMaximumSizeForEncoding(CFStringGetLength(cfs), kCFStringEncodingUTF8) + 1;
   outBuff = (char *) malloc(outLen);
   CFStringGetCString(cfs, outBuff, outLen, kCFStringEncodingUTF8);
   CFRelease(cfs);

   free(inBuff);
   return outBuff;
#endif /* __APPLE__ */
#if !defined(_WIN32) && !defined(__APPLE__)
   iconv_t ic;
   size_t i, size;
   char *inBuff, *outBuff;
   char *inFile, *outFile;
   size_t inLen, outLen;

   inLen = MMDFiles_strlen(str);
   if(inLen <= 0)
      return NULL;
   outLen = inLen * MMDFILESUTILS_MAXCHARBYTE;

   ic = iconv_open(MMDFILES_CHARSET, "SJIS");
   if(ic < 0)
      return NULL;

   inBuff = inFile = MMDFiles_strdup(str);
   outBuff = outFile = (char *) calloc(outLen, sizeof(char));

   /* convert directory separator */
   for(i = 0; i < inLen; i += size) {
      size = MMDFiles_getcharsize(&inFile[i]);
      if(size == 1 && MMDFiles_dirseparator(inFile[i]) == true)
         inFile[i] = MMDFILES_DIRSEPARATOR;
   }

   /* convert muli-byte char */
   if(iconv(ic, &inFile, &inLen, &outFile, &outLen) >= 0) {
      outFile = '\0';
   } else {
      strcpy(outBuff, "");
   }

   iconv_close(ic);

   free(inBuff);
   return outBuff;
#endif /* !_WIN32 && !__APPLE__ */
}