⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 avilib.c

📁 一个用于智能手机的多媒体库适合S60 WinCE的跨平台开发库
💻 C
📖 第 1 页 / 共 5 页
字号:
		+ 4+4+2+1+1+4+4+8+4;	}    }    towrite += len + (len&1) + 8;    //GF_LOG(GF_LOG_DEBUG, GF_LOG_CONTAINER, ("[avilib] ODML: towrite = 0x%llX = %lld\n", towrite, towrite));    if (AVI->video_superindex && 	    (s64)(AVI->pos+towrite) > (s64)((s64)NEW_RIFF_THRES*AVI->video_superindex->nEntriesInUse)) {	GF_LOG(GF_LOG_DEBUG, GF_LOG_CONTAINER, ("[avilib] Adding a new RIFF chunk: %d\n", AVI->video_superindex->nEntriesInUse));	// rotate ALL indices	AVI->video_superindex->nEntriesInUse++;	cur_std_idx = AVI->video_superindex->nEntriesInUse-1;	if (AVI->video_superindex->nEntriesInUse > NR_IXNN_CHUNKS) {	    GF_LOG(GF_LOG_ERROR, GF_LOG_CONTAINER, ("[avilib] Internal error in avilib - redefine NR_IXNN_CHUNKS\n"));	    GF_LOG(GF_LOG_DEBUG, GF_LOG_CONTAINER, ("[avilib] cur_std_idx=%d NR_IXNN_CHUNKS=%d"		    "POS=%lld towrite=%lld\n",		    cur_std_idx,NR_IXNN_CHUNKS, AVI->pos, towrite));	    return -1;	}	if (avi_add_std_index (AVI, (unsigned char *)"ix00", (unsigned char *)"00db", AVI->video_superindex->stdindex[ cur_std_idx ]) < 0) 	    return -1;	for (audtr = 0; audtr < AVI->anum; audtr++) {	    char aud[5];	    if (!AVI->track[audtr].audio_superindex) {		// not initialized -> no index		continue;	    }	    AVI->track[audtr].audio_superindex->nEntriesInUse++;	    sprintf(fcc, "ix%02d", audtr+1);	    sprintf(aud, "0%01dwb", audtr+1);	    if (avi_add_std_index (AVI, (unsigned char *)fcc, (unsigned char *)aud, AVI->track[audtr].audio_superindex->stdindex[ 			AVI->track[audtr].audio_superindex->nEntriesInUse - 1 ]) < 0	       ) return -1;	}	// write the new riff;	if (cur_std_idx > 0) {	    // dump the _previous_ == already finished index	    avi_ixnn_entry (AVI, AVI->video_superindex->stdindex[cur_std_idx - 1], 		    &AVI->video_superindex->aIndex[cur_std_idx - 1]);	    AVI->video_superindex->aIndex[cur_std_idx - 1].dwDuration = 		AVI->video_superindex->stdindex[cur_std_idx - 1]->nEntriesInUse - 1;	    for (audtr = 0; audtr < AVI->anum; audtr++) {		if (!AVI->track[audtr].audio_superindex) {		    // not initialized -> no index		    continue;		}		avi_ixnn_entry (AVI, AVI->track[audtr].audio_superindex->stdindex[cur_std_idx - 1], 			&AVI->track[audtr].audio_superindex->aIndex[cur_std_idx - 1]);		AVI->track[audtr].audio_superindex->aIndex[cur_std_idx - 1].dwDuration = 		    AVI->track[audtr].audio_superindex->stdindex[cur_std_idx - 1]->nEntriesInUse - 1;		if (AVI->track[audtr].a_fmt == 0x1) {		    AVI->track[audtr].audio_superindex->aIndex[cur_std_idx - 1].dwDuration *= 			AVI->track[audtr].a_bits*AVI->track[audtr].a_rate*AVI->track[audtr].a_chans/800;		}	    }	    // XXX: dump idx1 structure	    if (cur_std_idx == 1) {		avi_add_chunk(AVI, (unsigned char *)"idx1", (unsigned char *)AVI->idx, AVI->n_idx*16);		// qwBaseOffset will contain the start of the second riff chunk	    }	    // Fix the Offsets later at closing time	    avi_add_chunk(AVI, (unsigned char *)"RIFF", (unsigned char *)"AVIXLIST\0\0\0\0movi", 16);	    AVI->video_superindex->stdindex[ cur_std_idx ]->qwBaseOffset = AVI->pos -16 -8;#ifdef DEBUG_ODML	    GF_LOG(GF_LOG_DEBUG, GF_LOG_CONTAINER, ("[avilib] ODML: RIFF No.%02d at Offset 0x%llX\n", cur_std_idx, AVI->pos -16 -8));#endif	    for (audtr = 0; audtr < AVI->anum; audtr++) {		if (AVI->track[audtr].audio_superindex)		    AVI->track[audtr].audio_superindex->stdindex[ cur_std_idx ]->qwBaseOffset = 			AVI->pos -16 -8;			    }	    // now we can be sure	    AVI->is_opendml++;	}    }    if (video) {	avi_add_odml_index_entry_core(AVI, flags, AVI->pos, len, 		AVI->video_superindex->stdindex[ AVI->video_superindex->nEntriesInUse-1 ]);	AVI->total_frames++;    } // video    if (audio) {	avi_add_odml_index_entry_core(AVI, flags, AVI->pos, len, 		AVI->track[AVI->aptr].audio_superindex->stdindex[ 		        AVI->track[AVI->aptr].audio_superindex->nEntriesInUse-1 ]);    }    return 0;}// #undef NR_IXNN_CHUNKSstatic int avi_add_index_entry(avi_t *AVI, unsigned char *tag, long flags, u64 pos, u64 len){   void *ptr;   if(AVI->n_idx>=AVI->max_idx) {     ptr = realloc((void *)AVI->idx,(AVI->max_idx+4096)*16);          if(ptr == 0) {       AVI_errno = AVI_ERR_NO_MEM;       return -1;     }     AVI->max_idx += 4096;     AVI->idx = (unsigned char((*)[16]) ) ptr;   }      /* Add index entry */   //   GF_LOG(GF_LOG_DEBUG, GF_LOG_CONTAINER, ("[avilib] INDEX %s %ld %lu %lu\n", tag, flags, pos, len));   memcpy(AVI->idx[AVI->n_idx],tag,4);   long2str(AVI->idx[AVI->n_idx]+ 4,flags);   long2str(AVI->idx[AVI->n_idx]+ 8, (s32) pos);   long2str(AVI->idx[AVI->n_idx]+12, (s32) len);      /* Update counter */   AVI->n_idx++;   if(len>AVI->max_len) AVI->max_len=(u32) len;   return 0;}/* Returns 1 if more audio is in that video junk */int AVI_can_read_audio(avi_t *AVI){   if(AVI->mode==AVI_MODE_WRITE) { return -1; }   if(!AVI->video_index)         { return -1; }   if(!AVI->track[AVI->aptr].audio_index)         { return -1; }         // is it -1? the last ones got left out --tibit    //if (AVI->track[AVI->aptr].audio_posc>=AVI->track[AVI->aptr].audio_chunks-1) {   if (AVI->track[AVI->aptr].audio_posc>=AVI->track[AVI->aptr].audio_chunks) {       return 0;   }   if (AVI->video_pos >= AVI->video_frames) return 1;      if (AVI->track[AVI->aptr].audio_index[AVI->track[AVI->aptr].audio_posc].pos < AVI->video_index[AVI->video_pos].pos) return 1;   else return 0;}/*   AVI_open_output_file: Open an AVI File and write a bunch                         of zero bytes as space for the header.   returns a pointer to avi_t on success, a zero pointer on error*/GF_EXPORTavi_t* AVI_open_output_file(char * filename){   avi_t *AVI;   int i;   unsigned char AVI_header[HEADERBYTES];   /* Allocate the avi_t struct and zero it */   AVI = (avi_t *) malloc(sizeof(avi_t));   if(AVI==0)   {      AVI_errno = AVI_ERR_NO_MEM;      return 0;   }   memset((void *)AVI,0,sizeof(avi_t));   AVI->fdes = gf_f64_open(filename, "w+b");   if (!AVI->fdes )   {      AVI_errno = AVI_ERR_OPEN;      free(AVI);      return 0;   }   /* Write out HEADERBYTES bytes, the header will go here      when we are finished with writing */   for (i=0;i<HEADERBYTES;i++) AVI_header[i] = 0;   i = avi_write(AVI->fdes,(char *)AVI_header,HEADERBYTES);   if (i != HEADERBYTES)   {      fclose(AVI->fdes);      AVI_errno = AVI_ERR_WRITE;      free(AVI);      return 0;   }   AVI->pos  = HEADERBYTES;   AVI->mode = AVI_MODE_WRITE; /* open for writing */   //init   AVI->anum = 0;   AVI->aptr = 0;   return AVI;}GF_EXPORTvoid AVI_set_video(avi_t *AVI, int width, int height, double fps, char *compressor){   /* may only be called if file is open for writing */   if(AVI->mode==AVI_MODE_READ) return;   AVI->width  = width;   AVI->height = height;   AVI->fps    = fps;      if(strncmp(compressor, "RGB", 3)==0) {     memset(AVI->compressor, 0, 4);   } else {     memcpy(AVI->compressor,compressor,4);   }           AVI->compressor[4] = 0;   avi_update_header(AVI);}void AVI_set_audio(avi_t *AVI, int channels, long rate, int bits, int format, long mp3rate){   /* may only be called if file is open for writing */   if(AVI->mode==AVI_MODE_READ) return;   //inc audio tracks   AVI->aptr=AVI->anum;   ++AVI->anum;   if(AVI->anum > AVI_MAX_TRACKS) {     GF_LOG(GF_LOG_ERROR, GF_LOG_CONTAINER, ("[avilib] error - only %d audio tracks supported\n", AVI_MAX_TRACKS));     exit(1);   }   AVI->track[AVI->aptr].a_chans = channels;   AVI->track[AVI->aptr].a_rate  = rate;   AVI->track[AVI->aptr].a_bits  = bits;   AVI->track[AVI->aptr].a_fmt   = format;   AVI->track[AVI->aptr].mp3rate = mp3rate;   avi_update_header(AVI);}#define OUT4CC(s) \   if(nhb<=HEADERBYTES-4) memcpy(AVI_header+nhb,s,4); nhb += 4#define OUTLONG(n) \   if(nhb<=HEADERBYTES-4) long2str(AVI_header+nhb, (s32)(n)); nhb += 4#define OUTSHRT(n) \   if(nhb<=HEADERBYTES-2) { \      AVI_header[nhb  ] = (u8) ((n   )&0xff); \      AVI_header[nhb+1] = (u8) ((n>>8)&0xff); \   } \   nhb += 2#define OUTCHR(n) \   if(nhb<=HEADERBYTES-1) { \      AVI_header[nhb  ] = (n   )&0xff; \   } \   nhb += 1#define OUTMEM(d, s) \   { \     u32 s_ = (u32) (s); \     if(nhb + s_ <= HEADERBYTES) \        memcpy(AVI_header+nhb, (d), s_); \     nhb += s_; \   }//ThOe write preliminary AVI file header: 0 frames, max vid/aud sizeint avi_update_header(avi_t *AVI){   int njunk, sampsize, hasIndex, ms_per_frame, frate, flag;   int movi_len, hdrl_start, strl_start;   u32 j;   unsigned char AVI_header[HEADERBYTES];   u32 nhb;   unsigned long xd_size, xd_size_align2;   //assume max size   movi_len = AVI_MAX_LEN - HEADERBYTES + 4;   //assume index will be written   hasIndex=1;   if(AVI->fps < 0.001) {     frate=0;     ms_per_frame=0;   } else {     frate = (int) (FRAME_RATE_SCALE*AVI->fps + 0.5);     ms_per_frame=(int) (1000000/AVI->fps + 0.5);   }   /* Prepare the file header */   nhb = 0;   /* The RIFF header */   OUT4CC ("RIFF");   OUTLONG(movi_len);    // assume max size   OUT4CC ("AVI ");   /* Start the header list */   OUT4CC ("LIST");   OUTLONG(0);        /* Length of list in bytes, don't know yet */   hdrl_start = nhb;  /* Store start position */   OUT4CC ("hdrl");   /* The main AVI header */   /* The Flags in AVI File header */#define AVIF_HASINDEX           0x00000010      /* Index at end of file */#define AVIF_MUSTUSEINDEX       0x00000020#define AVIF_ISINTERLEAVED      0x00000100#define AVIF_TRUSTCKTYPE        0x00000800      /* Use CKType to find key frames */#define AVIF_WASCAPTUREFILE     0x00010000#define AVIF_COPYRIGHTED        0x00020000   OUT4CC ("avih");   OUTLONG(56);                 /* # of bytes to follow */   OUTLONG(ms_per_frame);       /* Microseconds per frame */   //ThOe ->0    //   OUTLONG(10000000);           /* MaxBytesPerSec, I hope this will never be used */   OUTLONG(0);   OUTLONG(0);                  /* PaddingGranularity (whatever that might be) */                                /* Other sources call it 'reserved' */   flag = AVIF_ISINTERLEAVED;   if(hasIndex) flag |= AVIF_HASINDEX;   if(hasIndex && AVI->must_use_index) flag |= AVIF_MUSTUSEINDEX;   OUTLONG(flag);               /* Flags */   OUTLONG(0);                  // no frames yet   OUTLONG(0);                  /* InitialFrames */   OUTLONG(AVI->anum+1);   OUTLONG(0);                  /* SuggestedBufferSize */   OUTLONG(AVI->width);         /* Width */   OUTLONG(AVI->height);        /* Height */                                /* MS calls the following 'reserved': */   OUTLONG(0);                  /* TimeScale:  Unit used to measure time */   OUTLONG(0);                  /* DataRate:   Data rate of playback     */   OUTLONG(0);                  /* StartTime:  Starting time of AVI data */   OUTLONG(0);                  /* DataLength: Size of AVI data chunk    */   /* Start the video stream list ---------------------------------- */   OUT4CC ("LIST");   OUTLONG(0);        /* Length of list in bytes, don't know yet */   strl_start = nhb;  /* Store start position */   OUT4CC ("strl");   /* The video stream header */   OUT4CC ("strh");   OUTLONG(56);                 /* # of bytes to follow */   OUT4CC ("vids");             /* Type */   OUT4CC (AVI->compressor);    /* Handler */   OUTLONG(0);                  /* Flags */   OUTLONG(0);                  /* Reserved, MS says: wPriority, wLanguage */   OUTLONG(0);                  /* InitialFrames */   OUTLONG(FRAME_RATE_SCALE);              /* Scale */   OUTLONG(frate);              /* Rate: Rate/Scale == samples/second */   OUTLONG(0);                  /* Start */   OUTLONG(0);                  // no frames yet   OUTLONG(0);                  /* SuggestedBufferSize */   OUTLONG(-1);                 /* Quality */   OUTLONG(0);                  /* SampleSize */   OUTLONG(0);                  /* Frame */   OUTLONG(0);                  /* Frame */   //   OUTLONG(0);                  /* Frame */   //OUTLONG(0);                  /* Frame */   /* The video stream format */   xd_size        = AVI->extradata_size;   xd_size_align2 = (AVI->extradata_size+1) & ~1;   OUT4CC ("strf");   OUTLONG(40 + xd_size_align2);/* # of bytes to follow */   OUTLONG(40 + xd_size);	/* Size */   OUTLONG(AVI->width);         /* Width */   OUTLONG(AVI->height);        /* Height */   OUTSHRT(1); OUTSHRT(24);     /* Planes, Count */   OUT4CC (AVI->compressor);    /* Compression */   // ThOe (*3)   OUTLONG(AVI->width*AVI->height*3);  /* SizeImage (in bytes?) */   OUTLONG(0);                  /* XPelsPerMeter */   OUTLONG(0);                  /* YPelsPerMeter */   OUTLONG(0);                  /* ClrUsed: Number of colors used */   OUTLONG(0);                  /* ClrImportant: Number of colors important */   // write extradata   if (xd_size > 0 && AVI->extradata) {      OUTMEM(AVI->extradata, xd_size);      if (xd_size != xd_size_align2) {         OUTCHR(0);      }

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -