avi_file.cpp
上传用户:sun1608
上传日期:2007-02-02
资源大小:6116k
文件大小:7k
源码类别:

流媒体/Mpeg4/MP4

开发平台:

Visual C++

  1. /*
  2.  * The contents of this file are subject to the Mozilla Public
  3.  * License Version 1.1 (the "License"); you may not use this file
  4.  * except in compliance with the License. You may obtain a copy of
  5.  * the License at http://www.mozilla.org/MPL/
  6.  * 
  7.  * Software distributed under the License is distributed on an "AS
  8.  * IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or
  9.  * implied. See the License for the specific language governing
  10.  * rights and limitations under the License.
  11.  * 
  12.  * The Original Code is MPEG4IP.
  13.  * 
  14.  * The Initial Developer of the Original Code is Cisco Systems Inc.
  15.  * Portions created by Cisco Systems Inc. are
  16.  * Copyright (C) Cisco Systems Inc. 2000, 2001.  All Rights Reserved.
  17.  * 
  18.  * Contributor(s): 
  19.  *              Bill May        wmay@cisco.com
  20.  */
  21. /*
  22.  * avi_file.cpp - provides generic class for avi file access control.
  23.  * file access is then used by avi audio and video bytestreams.
  24.  */
  25. #include "systems.h"
  26. #include "player_session.h"
  27. #include "player_media.h"
  28. #include "player_util.h"
  29. #include "media_utils.h"
  30. #include "avi_bytestream.h"
  31. #include "avi_file.h"
  32. #include "codec_plugin_private.h"
  33. static void close_avi_file (void *data)
  34. {
  35.   CAviFile *Avifile1 = (CAviFile *)data;
  36.   if (Avifile1 != NULL) {
  37.     delete Avifile1;
  38.     Avifile1 = NULL;
  39.   }
  40. }
  41. /*
  42.  * Create the media for the quicktime file, and set up some session stuff.
  43.  */
  44. int create_media_for_avi_file (CPlayerSession *psptr, 
  45.        const char *name,
  46.        char *errmsg,
  47.        uint32_t errlen,
  48.        int have_audio_driver,
  49.        control_callback_vft_t *cc_vft)
  50. {
  51.   CAviFile *Avifile1 = NULL;
  52.   avi_t *avi;
  53.   CPlayerMedia *mptr;
  54.   avi = AVI_open_input_file(name, 1);
  55.   if (avi == NULL) {
  56.     snprintf(errmsg, errlen, AVI_strerror());
  57.     player_error_message(errmsg);
  58.     return (-1);
  59.   }
  60.   int video_count = 1;
  61.   codec_plugin_t *plugin;
  62.   video_query_t vq;
  63.   const char *codec_name = AVI_video_compressor(avi);
  64.   player_debug_message("Trying avi video codec %s", codec_name);
  65.   plugin = check_for_video_codec(codec_name, 
  66.  NULL,
  67.  -1,
  68.  -1,
  69.  NULL,
  70.  0);
  71.   if (plugin == NULL) {
  72.     video_count = 0;
  73.     return -1;
  74.   } else {
  75.     vq.track_id = 1;
  76.     vq.compressor = codec_name;
  77.     vq.type = -1;
  78.     vq.profile = -1;
  79.     vq.fptr = NULL;
  80.     vq.h = AVI_video_height(avi);
  81.     vq.w = AVI_video_width(avi);
  82.     vq.frame_rate = AVI_video_frame_rate(avi);
  83.     vq.config = NULL;
  84.     vq.config_len = 0;
  85.     vq.enabled = 0;
  86.     vq.reference = NULL;
  87.   }
  88.   int have_audio = 0;
  89.   int audio_count = 0;
  90.   audio_query_t aq;
  91.   if (AVI_audio_bytes(avi) != 0) {
  92.     have_audio = 1;
  93.     plugin = check_for_audio_codec("AVI FILE",
  94.    NULL,
  95.    AVI_audio_format(avi), 
  96.    -1, 
  97.    NULL, 
  98.    0);
  99.     if (plugin != NULL) {
  100.       audio_count = 1;
  101.       aq.track_id = 1;
  102.       aq.compressor = "AVI_FILE";
  103.       aq.type = AVI_audio_format(avi);
  104.       aq.profile = -1;
  105.       aq.fptr = NULL;
  106.       aq.sampling_freq = AVI_audio_rate(avi);
  107.       aq.chans = AVI_audio_channels(avi);
  108.       aq.config = NULL;
  109.       aq.config_len = 0;
  110.       aq.enabled = 0;
  111.       aq.reference = NULL;
  112.     }
  113.   }
  114.   if (cc_vft != NULL && cc_vft->media_list_query != NULL) {
  115.     (cc_vft->media_list_query)(psptr, video_count, &vq, audio_count, &aq);
  116.   } else {
  117.     if (video_count != 0) vq.enabled = 1;
  118.     if (audio_count != 0) aq.enabled = 1;
  119.   }
  120.   if ((video_count == 0 || vq.enabled == 0) && 
  121.       (audio_count == 0 || aq.enabled == 0)) {
  122.     snprintf(errmsg, errlen, "No audio or video tracks enabled or playable");
  123.     AVI_close(avi);
  124.     return -1;
  125.   }
  126.   
  127.   Avifile1 = new CAviFile(name, avi, vq.enabled, audio_count);
  128.   psptr->set_media_close_callback(close_avi_file, Avifile1);
  129.   if (video_count != 0 && vq.enabled) {
  130.     mptr = new CPlayerMedia(psptr);
  131.     if (mptr == NULL) {
  132.       return (-1);
  133.     }
  134.   
  135.     video_info_t *vinfo = MALLOC_STRUCTURE(video_info_t);
  136.     if (vinfo == NULL) 
  137.       return (-1);
  138.     vinfo->height = vq.h;
  139.     vinfo->width = vq.w;
  140.     player_debug_message("avi file h %d w %d frame rate %g", 
  141.  vinfo->height,
  142.  vinfo->width,
  143.  vq.frame_rate);
  144.     plugin = check_for_video_codec(codec_name, 
  145.    NULL,
  146.    -1,
  147.    -1,
  148.    NULL,
  149.    0);
  150.     int ret;
  151.     ret = mptr->create_video_plugin(plugin,
  152.     NULL,
  153.     vinfo,
  154.     NULL,
  155.     0);
  156.     if (ret < 0) {
  157.       snprintf(errmsg, errlen, "Failed to create video plugin %s", 
  158.        codec_name);
  159.       player_error_message("Failed to create plugin data");
  160.       delete mptr;
  161.       return -1;
  162.     }
  163.     CAviVideoByteStream *vbyte = new CAviVideoByteStream(Avifile1);
  164.     if (vbyte == NULL) {
  165.       delete mptr;
  166.       return (-1);
  167.     }
  168.     vbyte->config(AVI_video_frames(avi), vq.frame_rate);
  169.     ret = mptr->create_from_file(vbyte, TRUE);
  170.     if (ret != 0) {
  171.       return (-1);
  172.     }
  173.   }
  174.     
  175.   int seekable = 1;
  176.   if (have_audio_driver > 0 && audio_count > 0 && aq.enabled != 0) {
  177.     plugin = check_for_audio_codec("AVI FILE",
  178.    NULL,
  179.    aq.type,
  180.    -1, 
  181.    NULL, 
  182.    0);
  183.     CAviAudioByteStream *abyte;
  184.     mptr = new CPlayerMedia(psptr);
  185.     if (mptr == NULL) {
  186.       return (-1);
  187.     }
  188.     audio_info_t *ainfo;
  189.     ainfo = MALLOC_STRUCTURE(audio_info_t);
  190.     ainfo->freq = aq.sampling_freq;
  191.     ainfo->chans = aq.chans;
  192.     ainfo->bitspersample = AVI_audio_bits(avi); 
  193.   
  194.     int ret;
  195.     ret = mptr->create_audio_plugin(plugin, 
  196.     NULL, 
  197.     ainfo,
  198.     NULL, 
  199.     0);
  200.     if (ret < 0) {
  201.       delete mptr;
  202.       player_error_message("Couldn't create audio from plugin %s", 
  203.    plugin->c_name);
  204.       return -1;
  205.     }
  206.     abyte = new CAviAudioByteStream(Avifile1);
  207.     ret = mptr->create_from_file(abyte, FALSE);
  208.     if (ret != 0) {
  209.       return (-1);
  210.     }
  211.     seekable = 0;
  212.   } 
  213.   psptr->session_set_seekable(seekable);
  214.   if (audio_count == 0 && have_audio != 0) {
  215.     snprintf(errmsg, errlen, "Unknown Audio Codec in avi file ");
  216.     return (1);
  217.   }
  218.   if (video_count != 1) {
  219.     snprintf(errmsg, errlen, "Unknown Video Codec %s in avi file",
  220.      codec_name);
  221.     return (1);
  222.   }
  223.   return (0);
  224. }
  225. CAviFile::CAviFile (const char *name, avi_t *avi,
  226.     int at, int vt)
  227. {
  228.   m_name = strdup(name);
  229.   m_file = avi;
  230.   m_file_mutex = SDL_CreateMutex();
  231.   m_video_tracks = vt;
  232.   m_audio_tracks = at;
  233. }
  234. CAviFile::~CAviFile (void)
  235. {
  236.   free(m_name);
  237.   m_name = NULL;
  238.   AVI_close(m_file);
  239.   if (m_file_mutex) {
  240.     SDL_DestroyMutex(m_file_mutex);
  241.     m_file_mutex = NULL;
  242.   }
  243. }
  244. /* end file avi_file.cpp */