如何将多个avi视频,合并到一起!(可以根据自己的需要设置每个avi视频的开始结束时间,然后合并到一起)
希望贴代码看看!!!

解决方案 »

  1.   

    不知道lz是否了解avi文件的格式。了解到话就好办了。
    每个avi文件都有一个头,先要把头写好,然后再把各个avi文件里的数据读出来,写到头后面就可以了。
    如果你还不太明白的话就去看看avi文件的格式。
    写avi文件的代码网上应该也有很多,可以下载下来参考一下。
      

  2.   

    参考下DShow里面des部分的内容,里面有一些合并多个视频的内容,还有视频间切换的方法。不想看英文的话,可以参考下陆其明那本书。应该有点帮助。
      

  3.   

    可以看看dshow 的sample里的TimelineTest工程
    贴部分代码如下int TimelineTest( )
    {
        USES_CONVERSION;
        HRESULT hr;    // use the ATL libraries to do automatic reference counting on pointers
        //
        CComPtr< IRenderEngine >  pRenderEngine;
        CComPtr< IGraphBuilder >  pGraph;
        CComPtr< IVideoWindow >   pVidWindow;
        CComPtr< IMediaEvent >    pEvent;
        CComPtr< IAMTimeline >    pTimeline;
        CComPtr< IAMTimelineObj > pVideoGroupObj;
        CComPtr< IAMTimelineObj > pAudioGroupObj;
        CComPtr< IMediaControl >  pControl;
        CComPtr< IMediaSeeking >  pSeeking;    //--------------------------------------------
        // make the timeline
        //--------------------------------------------    hr = CoCreateInstance(
                             CLSID_AMTimeline, 
                             NULL, 
                             CLSCTX_INPROC_SERVER, 
                             IID_IAMTimeline, 
                             (void**) &pTimeline 
                             );    if(FAILED( hr )) {
            Err(_T("Could not create timeline"));
            return hr;
        }    //--------------------------------------------
        // make the root group/composition
        //--------------------------------------------    hr = pTimeline->CreateEmptyNode( &pVideoGroupObj, TIMELINE_MAJOR_TYPE_GROUP );
        if(FAILED( hr )) 
        {
            Err(_T("Could not create empty node"));
            return hr;
        }    CComQIPtr< IAMTimelineGroup, &IID_IAMTimelineGroup > pVideoGroup( pVideoGroupObj );
        CMediaType VideoGroupType;    // all we set is the major type. The group will automatically use other defaults
        VideoGroupType.SetType( &MEDIATYPE_Video );
        hr = pVideoGroup->SetMediaType( &VideoGroupType );
        if(FAILED( hr )) 
        {
            Err(_T("Could not set media type"));
            return hr;
        }    //--------------------------------------------
        // add the group to the timeline
        //--------------------------------------------    hr = pTimeline->AddGroup( pVideoGroupObj );
        if(FAILED( hr )) 
        {
            Err(_T("Could not add video group"));
            return hr;
        }    //--------------------------------------------
        // make a track
        //--------------------------------------------    CComPtr< IAMTimelineObj > pTrack1Obj;
        hr = pTimeline->CreateEmptyNode( &pTrack1Obj, TIMELINE_MAJOR_TYPE_TRACK );
        if(FAILED( hr )) 
        {
            Err(_T("Could not create empty track"));
            return hr;
        }    //--------------------------------------------
        // tell the composition about the track
        //--------------------------------------------    CComQIPtr< IAMTimelineComp, &IID_IAMTimelineComp > pRootComp( pVideoGroupObj );
        hr = pRootComp->VTrackInsBefore( pTrack1Obj, -1 );
        if(FAILED( hr )) 
        {
            Err(_T("Could not insert track"));
            return hr;
        }    //--------------------------------------------
        // create a source from 0 to 8 seconds
        //--------------------------------------------    REFERENCE_TIME TLStart = 0 * UNITS;
        REFERENCE_TIME TLStop = 8 * UNITS;    // you can set these if you want to other numbers, and the video will 
        // speed up or slow down if the duration isn't the same as the timeline's.
        REFERENCE_TIME MediaStart = 0 * UNITS;
        REFERENCE_TIME MediaStop = 8 * UNITS;    // Search around for directory of media files
        TCHAR tBasePath[MAX_PATH] = {0};
        TCHAR* strLastSlash = NULL;
        GetModuleFileName( NULL, tBasePath, MAX_PATH );
        tBasePath[MAX_PATH-1]=0;
        strLastSlash = _tcsrchr( tBasePath, TEXT('\\') );
        if( strLastSlash )
            *strLastSlash = 0;    WCHAR pClipname[_MAX_PATH+_MAX_PATH+2];   // make room for both the strings    (void)StringCchCopyW( pClipname, NUMELMS(pClipname),T2W( tBasePath ) );
        (void)StringCchCatW( pClipname, NUMELMS(pClipname),L"\\" );
        (void)StringCchCatW( pClipname, NUMELMS(pClipname),wszVideo1Name );    // Make sure that this file exists
        DWORD dwAttr = GetFileAttributesW(pClipname);
        if(dwAttr == (DWORD) -1)
        {
            (void)StringCchCopyW( pClipname,NUMELMS(pClipname), T2W( tBasePath ) );
            (void)StringCchCatW( pClipname,NUMELMS(pClipname), L"\\..\\" );
            (void)StringCchCatW( pClipname,NUMELMS(pClipname), wszVideo1Name );
            dwAttr = GetFileAttributesW(pClipname);
            if(dwAttr == (DWORD) -1)
            {
                (void)StringCchCopyW( pClipname,NUMELMS(pClipname), T2W( tBasePath ) );
                (void)StringCchCatW( pClipname,NUMELMS(pClipname), L"\\..\\..\\" );
                (void)StringCchCatW( pClipname,NUMELMS(pClipname), wszVideo1Name );
                dwAttr = GetFileAttributesW(pClipname);
                if(dwAttr == (DWORD) -1)
                {
                    (void)StringCchCopyW( pClipname,NUMELMS(pClipname), T2W( tBasePath ) );
                    (void)StringCchCatW( pClipname,NUMELMS(pClipname), L"\\..\\Editing\\TimelineTest\\" );
                    (void)StringCchCatW( pClipname,NUMELMS(pClipname), wszVideo1Name );
                }
            }
        }
        WCHAR* strLastSlashW = wcsrchr( pClipname, L'\\' );
        if( strLastSlashW )
            *strLastSlashW = 0;
        (void)StringCchCopy( tBasePath, NUMELMS(tBasePath), W2T(pClipname)  );    (void)StringCchCopyW( pClipname, NUMELMS(pClipname),T2W( tBasePath ) );
        (void)StringCchCatW( pClipname, NUMELMS(pClipname),L"\\" );
        (void)StringCchCatW( pClipname, NUMELMS(pClipname),wszVideo1Name );    // create the timeline source
        //
        CComPtr<IAMTimelineObj> pSource1Obj;
        hr = pTimeline->CreateEmptyNode( &pSource1Obj, TIMELINE_MAJOR_TYPE_SOURCE );
        if(FAILED( hr )) 
        {
            Err(_T("Could not create the timeline source"));
            return hr;
        }    // set up source right
        //
        hr = pSource1Obj->SetStartStop( TLStart, TLStop );
        CComQIPtr< IAMTimelineSrc, &IID_IAMTimelineSrc > pSource1Src( pSource1Obj );    hr |= pSource1Src->SetMediaTimes( MediaStart, MediaStop );
        hr |= pSource1Src->SetMediaName( pClipname );
        if(FAILED( hr )) 
        {
            Err(_T("Could not configure media source"));
            return E_FAIL;
        }    //--------------------------------------------
        // tell the track about the source
        //--------------------------------------------    CComQIPtr< IAMTimelineTrack, &IID_IAMTimelineTrack > pTrack1( pTrack1Obj );
        hr = pTrack1->SrcAdd( pSource1Obj );
        if(FAILED( hr )) 
        {
            Err(_T("Could not add source to track"));
            return hr;
        }
        
      

  4.   

    可以看看dshow 的sample里的TimelineTest工程
    贴部分代码如下int TimelineTest( )
    {
        USES_CONVERSION;
        HRESULT hr;    // use the ATL libraries to do automatic reference counting on pointers
        //
        CComPtr< IRenderEngine >  pRenderEngine;
        CComPtr< IGraphBuilder >  pGraph;
        CComPtr< IVideoWindow >   pVidWindow;
        CComPtr< IMediaEvent >    pEvent;
        CComPtr< IAMTimeline >    pTimeline;
        CComPtr< IAMTimelineObj > pVideoGroupObj;
        CComPtr< IAMTimelineObj > pAudioGroupObj;
        CComPtr< IMediaControl >  pControl;
        CComPtr< IMediaSeeking >  pSeeking;    //--------------------------------------------
        // make the timeline
        //--------------------------------------------    hr = CoCreateInstance(
                             CLSID_AMTimeline, 
                             NULL, 
                             CLSCTX_INPROC_SERVER, 
                             IID_IAMTimeline, 
                             (void**) &pTimeline 
                             );    if(FAILED( hr )) {
            Err(_T("Could not create timeline"));
            return hr;
        }    //--------------------------------------------
        // make the root group/composition
        //--------------------------------------------    hr = pTimeline->CreateEmptyNode( &pVideoGroupObj, TIMELINE_MAJOR_TYPE_GROUP );
        if(FAILED( hr )) 
        {
            Err(_T("Could not create empty node"));
            return hr;
        }    CComQIPtr< IAMTimelineGroup, &IID_IAMTimelineGroup > pVideoGroup( pVideoGroupObj );
        CMediaType VideoGroupType;    // all we set is the major type. The group will automatically use other defaults
        VideoGroupType.SetType( &MEDIATYPE_Video );
        hr = pVideoGroup->SetMediaType( &VideoGroupType );
        if(FAILED( hr )) 
        {
            Err(_T("Could not set media type"));
            return hr;
        }    //--------------------------------------------
        // add the group to the timeline
        //--------------------------------------------    hr = pTimeline->AddGroup( pVideoGroupObj );
        if(FAILED( hr )) 
        {
            Err(_T("Could not add video group"));
            return hr;
        }    //--------------------------------------------
        // make a track
        //--------------------------------------------    CComPtr< IAMTimelineObj > pTrack1Obj;
        hr = pTimeline->CreateEmptyNode( &pTrack1Obj, TIMELINE_MAJOR_TYPE_TRACK );
        if(FAILED( hr )) 
        {
            Err(_T("Could not create empty track"));
            return hr;
        }    //--------------------------------------------
        // tell the composition about the track
        //--------------------------------------------    CComQIPtr< IAMTimelineComp, &IID_IAMTimelineComp > pRootComp( pVideoGroupObj );
        hr = pRootComp->VTrackInsBefore( pTrack1Obj, -1 );
        if(FAILED( hr )) 
        {
            Err(_T("Could not insert track"));
            return hr;
        }    //--------------------------------------------
        // create a source from 0 to 8 seconds
        //--------------------------------------------    REFERENCE_TIME TLStart = 0 * UNITS;
        REFERENCE_TIME TLStop = 8 * UNITS;    // you can set these if you want to other numbers, and the video will 
        // speed up or slow down if the duration isn't the same as the timeline's.
        REFERENCE_TIME MediaStart = 0 * UNITS;
        REFERENCE_TIME MediaStop = 8 * UNITS;    // Search around for directory of media files
        TCHAR tBasePath[MAX_PATH] = {0};
        TCHAR* strLastSlash = NULL;
        GetModuleFileName( NULL, tBasePath, MAX_PATH );
        tBasePath[MAX_PATH-1]=0;
        strLastSlash = _tcsrchr( tBasePath, TEXT('\\') );
        if( strLastSlash )
            *strLastSlash = 0;    WCHAR pClipname[_MAX_PATH+_MAX_PATH+2];   // make room for both the strings    (void)StringCchCopyW( pClipname, NUMELMS(pClipname),T2W( tBasePath ) );
        (void)StringCchCatW( pClipname, NUMELMS(pClipname),L"\\" );
        (void)StringCchCatW( pClipname, NUMELMS(pClipname),wszVideo1Name );    // Make sure that this file exists
        DWORD dwAttr = GetFileAttributesW(pClipname);
        if(dwAttr == (DWORD) -1)
        {
            (void)StringCchCopyW( pClipname,NUMELMS(pClipname), T2W( tBasePath ) );
            (void)StringCchCatW( pClipname,NUMELMS(pClipname), L"\\..\\" );
            (void)StringCchCatW( pClipname,NUMELMS(pClipname), wszVideo1Name );
            dwAttr = GetFileAttributesW(pClipname);
            if(dwAttr == (DWORD) -1)
            {
                (void)StringCchCopyW( pClipname,NUMELMS(pClipname), T2W( tBasePath ) );
                (void)StringCchCatW( pClipname,NUMELMS(pClipname), L"\\..\\..\\" );
                (void)StringCchCatW( pClipname,NUMELMS(pClipname), wszVideo1Name );
                dwAttr = GetFileAttributesW(pClipname);
                if(dwAttr == (DWORD) -1)
                {
                    (void)StringCchCopyW( pClipname,NUMELMS(pClipname), T2W( tBasePath ) );
                    (void)StringCchCatW( pClipname,NUMELMS(pClipname), L"\\..\\Editing\\TimelineTest\\" );
                    (void)StringCchCatW( pClipname,NUMELMS(pClipname), wszVideo1Name );
                }
            }
        }
        WCHAR* strLastSlashW = wcsrchr( pClipname, L'\\' );
        if( strLastSlashW )
            *strLastSlashW = 0;
        (void)StringCchCopy( tBasePath, NUMELMS(tBasePath), W2T(pClipname)  );    (void)StringCchCopyW( pClipname, NUMELMS(pClipname),T2W( tBasePath ) );
        (void)StringCchCatW( pClipname, NUMELMS(pClipname),L"\\" );
        (void)StringCchCatW( pClipname, NUMELMS(pClipname),wszVideo1Name );    // create the timeline source
        //
        CComPtr<IAMTimelineObj> pSource1Obj;
        hr = pTimeline->CreateEmptyNode( &pSource1Obj, TIMELINE_MAJOR_TYPE_SOURCE );
        if(FAILED( hr )) 
        {
            Err(_T("Could not create the timeline source"));
            return hr;
        }    // set up source right
        //
        hr = pSource1Obj->SetStartStop( TLStart, TLStop );
        CComQIPtr< IAMTimelineSrc, &IID_IAMTimelineSrc > pSource1Src( pSource1Obj );    hr |= pSource1Src->SetMediaTimes( MediaStart, MediaStop );
        hr |= pSource1Src->SetMediaName( pClipname );
        if(FAILED( hr )) 
        {
            Err(_T("Could not configure media source"));
            return E_FAIL;
        }    //--------------------------------------------
        // tell the track about the source
        //--------------------------------------------    CComQIPtr< IAMTimelineTrack, &IID_IAMTimelineTrack > pTrack1( pTrack1Obj );
        hr = pTrack1->SrcAdd( pSource1Obj );
        if(FAILED( hr )) 
        {
            Err(_T("Could not add source to track"));
            return hr;
        }