mms流媒体服务器搭建(包含预览即本地播放)

实现功能说明:
实现服务端与客户端视频文件实时播放功能即直播功能(注:服务端和客户端有延迟),服务端截图如下:
这里写图片描述
客户端可以使用vlc播放器通过如下地址播放:mms://127.0.0.1:8041(注:127.0.0.1是本机回环Ip,至于什么是回环IP,自己百度)
其他说明:
1.此流媒体开发是基于windows media encoder SDK开发,而这个sdk又需要依赖windows media encode中的库文件,因此,开发之前,先安装这两个软件,开发过程中只要包含windows media encoder SDK即可,下载地址为(window7亲测可用):http://download.csdn.net/download/zaokang5603/10028002
2.目前上面只支持windows的媒体文件,如果想要支持avi,rmvb视频各种,可以下载个编解码器,例如FinalCodecs,安装即可,无需额外配置
3.如果想要两边支持实时播放,且服务器这边可以有音频输出,那么可以在开始编码之后,可以使用wmPlayer控件,播放此文件,和预览的道理是一样的
4.以下代码是基于vs2013开发,工程下载地址为:http://download.csdn.net/download/zaokang5603/10118016
5.本人也是初次开发,哪里有问题,留言说明,莫喷!
代码片段如下:
#define RELEASE_PTR {\
if (pSrcGrpColl)\
{\
pSrcGrpColl->Release(); \
pSrcGrpColl = NULL; }\
if (pSrcGrp)\
{\
pSrcGrp->Release(); \
pSrcGrp = NULL; \
}\
if (pAudSrc)\
{\
pAudSrc->Release(); \
pAudSrc = NULL; \
}\
if (pVidSrc)\
{\
pVidSrc->Release(); \
pVidSrc = NULL; \
}\
if (pProColl)\
{\
pProColl->Release(); \
pProColl = NULL; \
}\
if (pPro)\
{\
pPro->Release(); \
pPro = NULL; \
}\
if (pPro2)\
{\
pPro2->Release(); \
pPro2 = NULL; \
}\
if (pBrdCst)\
{\
pBrdCst->Release(); \
pBrdCst = NULL; \
}\
if (pPreviewColl)\
{\
pPreviewColl->Release(); \
pPreviewColl = NULL; \
}\
}
void CmsdntestDlg::OnBnClickedButton1()//开启流媒体按钮
{
// TODO: 在此添加控件通知处理程序代码

CComBSTR serverFilePath;
{
    CFileDialog dlgFile(TRUE);
    if (dlgFile.DoModal() == IDOK)
    {
        CString file = dlgFile.GetPathName();
        serverFilePath = file.AllocSysString();
        //m_path = file.AllocSysString();
        //m_serverFilePath = WideCharToUTF8(bstr);
    }
}
CoUninitialize();//必须先要添加这一坨,可能dlgFile析构没有CoUninitialize造成流媒体广播一段时间就挂掉了
if (!Initencoder(serverFilePath))//搭建mms流媒体服务器
{
    AfxMessageBox("encoding file failed!");
    GetDlgItem(IDC_BUTTON1)->EnableWindow(FALSE);
    return;
}
SysFreeString(serverFilePath);
GetDlgItem(IDC_BUTTON1)->EnableWindow(FALSE);
}
    BOOL CmsdntestDlg::Initencoder(CComBSTR &filePath)
    {
        IWMEncSourceGroupCollection* pSrcGrpColl = NULL;
        IWMEncSourceGroup* pSrcGrp = NULL;
        IWMEncSource* pAudSrc = NULL;
        IWMEncSource* pVidSrc = NULL;
        IWMEncProfileCollection* pProColl = NULL;
        IWMEncProfile* pPro = NULL;
        IWMEncProfile2* pPro2 = NULL;
        IWMEncBroadcast* pBrdCst = NULL;
        IWMEncDataViewCollection* pPreviewColl = NULL;


//IWMEncProfile* pPro = NULL;


// Initialize the COM library and retrieve a pointer
// to an IWMEncoder interface.
if (FAILED(CoInitialize(NULL)))
{

    return FALSE;
}
if (!m_pEncoder)
{
    if (FAILED(CoCreateInstance(CLSID_WMEncoder,
        NULL,
        CLSCTX_INPROC_SERVER,
        IID_IWMEncoder,
        (void**)&m_pEncoder)))
    {
        return FALSE;
    }
}



// Retrieve a pointer to an IWMEncSourceGroupCollection
// interface.

if (FAILED(m_pEncoder->get_SourceGroupCollection(&pSrcGrpColl)))//获得解码器集合
{
    return FALSE;
}

// Add a new source group to the collection.

if (FAILED(pSrcGrpColl->Add(CComBSTR("SG_1"), &pSrcGrp)))//获得解码器组
{
    RELEASE_PTR;
    return FALSE;
}


// Add an audio and avideo source to the source group.

if (FAILED(pSrcGrp->AddSource(WMENC_AUDIO, &pAudSrc)))//添加音频资源
{
    RELEASE_PTR;
    return FALSE;
}
if (FAILED(pSrcGrp->AddSource(WMENC_VIDEO, &pVidSrc)))//添加视频资源
{
    RELEASE_PTR;
    return FALSE;
}
// Specify an .avi source file and a .wmv output file.
if (FAILED(pAudSrc->SetInput(filePath)))//获得文件音频源
{
    RELEASE_PTR;
    return FALSE;
}

if (FAILED(pVidSrc->SetInput(filePath)))//获得文件视频源
{
    RELEASE_PTR;
    return FALSE;
}


// Loop through the profile collection and retrieve a specific
// profile.
if (FAILED(m_pEncoder->get_ProfileCollection(&pProColl)))//获得配置集合
{
    RELEASE_PTR;
    return FALSE;
}

if (!creatprofile(&pPro2))//创建配置文件
{
    AfxMessageBox("creatProfile failed!");
    RELEASE_PTR;
    return FALSE;
}
if (FAILED(pPro2->QueryInterface(IID_IWMEncProfile, (void**)&pPro)))
{
    RELEASE_PTR;
    return FALSE;
}

if (FAILED(pSrcGrp->put_Profile(CComVariant(pPro))))//把配置文件配置给资源组,即解码器
{
    RELEASE_PTR;
    return FALSE;
}

if (!m_pPreview)
{
    if (FAILED(CoCreateInstance(CLSID_WMEncPreview,
        NULL,
        CLSCTX_INPROC_SERVER,
        IID_IWMEncDataView,
        (void**)&m_pPreview)))//创建预览对象
    {
        RELEASE_PTR;
        return FALSE;
    }
}



// Retrieve the preview collection.

if (FAILED(pVidSrc->get_PreviewCollection(&pPreviewColl)))//获取预览集合
{
    RELEASE_PTR;
    return FALSE;
}


// Add the preview object to the data view collection. If you set the
// cookie to -1, the encoding process automatically generates a unique
// cookie.


if (FAILED(pPreviewColl->Add(m_pPreview, &m_lCookie)))//把预览添加进预览集合
{
    RELEASE_PTR;
    return FALSE;
}

if (FAILED(m_pEncoder->get_Broadcast(&pBrdCst)))//广播
{
    RELEASE_PTR;
    return FALSE;
}
;

// Select the 5th profile from the collection and set it into the source group.
if (FAILED(pBrdCst->put_PortNumber(WMENC_PROTOCOL_HTTP, 8401)))//广播端口8401,即客户端通过 mms://127.0.0.1:8041地址即可观看直播,注:127.0.0.1是用当前服务器ip,非此ip
{
    RELEASE_PTR;
    return FALSE;
}


if (FAILED(m_pEncoder->PrepareToEncode(VARIANT_TRUE)))//准备开始编解码
{
    RELEASE_PTR;
    return FALSE;
}

HWND hWnd = GetDlgItem(IDC_STATIC)->GetSafeHwnd();
if (FAILED(m_pPreview->SetViewSetting((DWORD)m_lCookie,
    sizeof(hWnd),
    (BYTE*)&hWnd)))//获得picture control 句柄
{
    RELEASE_PTR;
    return FALSE;
}



if (FAILED(m_pEncoder->Start()))//开始编解码
{
    RELEASE_PTR;
    return FALSE;
}

if (FAILED(m_pPreview->Start(m_lCookie)))//开始预览播放
{
    RELEASE_PTR;
    return FALSE;
}
//IWMEncProfileCollection* pProColl = NULL;

RELEASE_PTR;

return TRUE;
}

BOOL CmsdntestDlg::creatprofile(IWMEncProfile2** pPro2)
{

IWMEncAudienceObj* pAudnc = NULL;
BOOL isOk = TRUE;

//以下各个参数代表什么,可以查看windows media encoder SDk帮助文档,有详细介绍
// Initialize the COM library and retrieve a pointer to an IWMEncProfile2 interface.
if (FAILED(CoCreateInstance(CLSID_WMEncProfile2,
    NULL,
    CLSCTX_INPROC_SERVER,
    IID_IWMEncProfile2,
    (void**)pPro2)))
{
    return FALSE;

}

// Verify profile settings immediately as they are set.
if (FAILED((*pPro2)->put_ValidateMode(VARIANT_TRUE)))
{

    return FALSE;
}

// Provide a name and description.
if (FAILED((*pPro2)->put_ProfileName(CComBSTR("Sample MBR Profile"))))
{

    return FALSE;
}
if (FAILED((*pPro2)->put_ProfileDescription(CComBSTR("A video profile with three audiences"))))
{

    return FALSE;
}

// specifies the type of content streams that the current profile supports
if (FAILED((*pPro2)->put_ContentType(17)))//每个数字代表不一样文件格式,具体查看Wmencoder SDk帮助文档
{

    return FALSE;
}

// Specify constant bit rate (CBR) mode.
if (FAILED((*pPro2)->put_VBRMode(WMENC_VIDEO, 0, WMENC_PVM_UNCONSTRAINED)))
{

    return FALSE;
}

// Add audiences for 200, 400, and 600 Kbps.
if (FAILED((*pPro2)->AddAudience(5000000, &pAudnc)))
{

    return FALSE;
}
if (FAILED(pAudnc->put_VideoCodec(0, 3)))
{
    pAudnc->Release();
    pAudnc = NULL;
    return FALSE;
}

// Make the video output size match the input size by setting height and width to 0.
if (FAILED(pAudnc->put_VideoHeight(0, 0)))
{
    pAudnc->Release();
    pAudnc = NULL;
    return FALSE;
}
if (FAILED(pAudnc->put_VideoWidth(0, 0)))
{
    pAudnc->Release();
    pAudnc = NULL;
    return FALSE;
}

// Change the buffer size to 5 seconds. By default, the end user's default setting is used.
if (FAILED(pAudnc->put_VideoBufferSize(0, 5000)))
{
    pAudnc->Release();
    pAudnc = NULL;
    return FALSE;
}

//specifies the video codec quality.

if (FAILED((*pPro2)->get_Audience(0, &pAudnc)))
{
    pAudnc->Release();
    pAudnc = NULL;
    return FALSE;
}

if (FAILED(pAudnc->put_VideoCompressionQuality(0, 80)))//视频压缩比例
{
    pAudnc->Release();
    pAudnc = NULL;
    return FALSE;
}

// Change the video image sharpness for the first audience only.
if (FAILED(pAudnc->put_VideoImageSharpness(0, 70)))
{
    pAudnc->Release();
    pAudnc = NULL;
    return FALSE;
}

// Validate the settings to make sure the profile has no errors.
if (FAILED((*pPro2)->Validate()))
{
    pAudnc->Release();
    pAudnc = NULL;
    return FALSE;
    }

    // Save the profile to a .prx file.
    /*if (FAILED((*pPro2)->SaveToFile(CComBSTR("D:\\test.prx"))))
    {
    printf("profile error:SaveToFile \n");
    }*/

    // Release pointers.
    if (pAudnc)
    {
        pAudnc->Release();
        pAudnc = NULL;
    }

    return TRUE;


    }


void CmsdntestDlg::OnBnClickedButton2()//关闭流媒体按钮
{
    // TODO:  在此添加控件通知处理程序代码
    if (m_pPreview)
    {
        m_pPreview->Stop(m_lCookie);
        m_pPreview->Release();
        m_pPreview = NULL;
    }
    if (m_pEncoder)
    {
        m_pEncoder->Stop();
        m_pEncoder->Release();
        m_pEncoder = NULL;
    }
    GetDlgItem(IDC_BUTTON1)->EnableWindow(TRUE);
    CoUninitialize();
}
  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
YOLO高分设计资源源码,详情请查看资源内容中使用说明 YOLO高分设计资源源码,详情请查看资源内容中使用说明 YOLO高分设计资源源码,详情请查看资源内容中使用说明 YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值