/************************************************* * Copyright (C), Xiongmai Information Technologies Co., Ltd. 2018-2019. All rights reserved. * 文件名: demo_rtsp.c * 作者@编号: XM R&D @02479 * 版本: V1.00 * 创建日期: 2019.03.01 * 功能描述: 演示Rtsp实时流媒体播放。 * * 修改历史: ** 1.日期: 2019.03.01 ** 修改者: XM R&D @02479 ** 修改内容: 首次创建 。 ** 2.日期: 2019.03.01 ** 修改者: XM R&D @02479 ** 修改内容: 完成了基础版。 *************************************************/ #include "demo_inc.h" #include "demo_mem.h" #include "demo_audio.h" #include "demo_video_enc.h" #include "demo_rtsp.h" #include "libxmrtsp_api.h" #include "demo_camera.h" typedef struct { rtsp_handle rtspHandle; XM_S32 bAudio; MaQueStreamChannel_e eStreamChn; XM_S32 bClosePrint; } RtspCallbackArg_s; static XM_S32 g_bRtspStop; static XM_S32 Demo_Rtsp_Audio_record_callback(XM_VOID *pUserArg, MaQueAudioFrameInfo_s *pstFrameInfo) { RtspCallbackArg_s *pstCallbackArg = (RtspCallbackArg_s *) pUserArg; MaQueTimeStamp_s *pstTimeStamp = &pstFrameInfo->stTimeStamp; MaQueSystemTime_s *pstSysTime = &pstTimeStamp->stSysTime; struct timeval stTimeVal; //INFO_PRINTF("Frame,Time: %ds + %dms\n", pstSysTime->second, pstFrameInfo->stTimeStamp.mSec); stTimeVal.tv_sec = pstSysTime->day * 24 * 60 * 60 + pstSysTime->hour * 60 * 60 + pstSysTime->minute * 60 + pstSysTime->second; stTimeVal.tv_usec = pstSysTime->second * 1000; rtp_send_media(pstCallbackArg->rtspHandle, 0, pstCallbackArg->eStreamChn, (XM_S8 *)pstFrameInfo->pData, pstFrameInfo->nDataLen, &stTimeVal); return XM_SUCCESS; } static XM_S32 Demo_Rtsp_Camera_DNC_callback (XM_VOID *pUserArg, XM_S32 bNightMode) { INFO_PRINTF("bNightMode: %d.\n", bNightMode); MaQueLedCfg_s stLedCfg; XM_S32 bOpen; if (bNightMode) { bOpen = 1; } else { bOpen = 0; } stLedCfg.bOpen = bOpen; stLedCfg.eLedMode = MAQUE_LED_MODE_AUTO; stLedCfg.eLedType = MAQUE_LED_TYPE_IR; LibXmMaQue_Camera_setLed(0, &stLedCfg); return XM_SUCCESS; } static XM_VOID *Demo_Rtsp_ResetLed_task(XM_VOID *pArg) { XM_U32 value; MaQueLedCfg_s stLedCfg; INFO_PRINTF("---------------- Rtsp_ResetLed Start -----------------!\n"); while(1) { LibXmMaQue_Misc_readResetKey(&value); if (!value) { stLedCfg.bOpen = 1; stLedCfg.eLedMode = MAQUE_LED_MODE_AUTO; stLedCfg.eLedType = MAQUE_LED_TYPE_WL; LibXmMaQue_Camera_setLed(0, &stLedCfg); sleep(3); stLedCfg.bOpen = 0; stLedCfg.eLedMode = MAQUE_LED_MODE_AUTO; stLedCfg.eLedType = MAQUE_LED_TYPE_WL; LibXmMaQue_Camera_setLed(0, &stLedCfg); } sleep(1); } return NULL; } static XM_S32 Demo_Rtsp_Audio_start(rtsp_handle rtspHandle) { XM_S32 res; RtspCallbackArg_s stCallbackArg; AudioRecordModParam_s stAudModParam = { 0 }; MaQueVqeCfg_s stMaQueVqeCfg; MaQueAudioEncodeFormat_s stAudEncFormat = { 0 }; StringValueGet_s astVidEncValGet[] = { {"bEnabled:", &stAudModParam.bEnabled, XM_VALUE_TYPE_INT, sizeof(stAudModParam.bEnabled)}, {"bWriteFile:", &stAudModParam.bWriteFile, XM_VALUE_TYPE_INT, sizeof(stAudModParam.bWriteFile)}, {"nDemoTimeSecs:", &stAudModParam.nDemoTimeSecs, XM_VALUE_TYPE_INT, sizeof(stAudModParam.nDemoTimeSecs)}, }; MaQue_Demo_File_parse512(MaQue_Demo_Common_getRefFile(), "RtspAudioRecord", astVidEncValGet, sizeof(astVidEncValGet) / sizeof(StringValueGet_s)); if (!stAudModParam.bEnabled) { INFO_PRINTF("if (!stAudModParam.bEnabled)\n"); return XM_FAILURE; } INFO_PRINTF(" ------------ Audio Record Start ---------------\n"); INFO_PRINTF("bWriteFile: %d, nDemoTimeSecs: %d.\n", stAudModParam.bWriteFile, stAudModParam.nDemoTimeSecs); stAudEncFormat.eEncType = MAQUE_AUDIO_ENCODE_G711_ALAW; stAudEncFormat.eSampleRate = MAQUE_AUDIO_SAMPLE_RATE_8000; stAudEncFormat.eSampleBits = MAQUE_AUDIO_SAMPLE_BITS_16; stAudEncFormat.bitrateKb = 0; /* G711A和G711U不需要设置比特率。*/ stCallbackArg.bAudio = 1; stCallbackArg.eStreamChn = RTSP_MEDIA_DWTYPE_AUDIO; stCallbackArg.rtspHandle = rtspHandle; res = LibXmMaQue_AudioEnc_create(0, &stAudEncFormat, Demo_Rtsp_Audio_record_callback, &stCallbackArg); if (res != XM_SUCCESS) { ERROR_PRINTF("LibXmMaQue_AudioEnc_create() Failed!\n"); return XM_FAILURE; } LibXmMaQue_Audio_setMicVolume(1, (30 << 8) | 46); LibXmMaQue_Audio_setSpeakerVolume(1, 15); res = LibXmMaQue_Audio_getAiVqeAttr(0, &stMaQueVqeCfg); if (res != XM_SUCCESS) { ERROR_PRINTF("LibXmMaQue_Audio_getAiVqeAttr() Failed!\n"); return XM_FAILURE; } stMaQueVqeCfg.bVqeEnable = 1; stMaQueVqeCfg.bAecEnable = 0; res = LibXmMaQue_Audio_setAiVqeAttr(0, &stMaQueVqeCfg); if (res != XM_SUCCESS) { ERROR_PRINTF("LibXmMaQue_Audio_getAiVqeAttr() Failed!\n"); return XM_FAILURE; } return XM_SUCCESS; } static XM_S32 Demo_Rtsp_getVideoStream_callback(XM_VOID *pUserArg, MaQueVideoEncFrameInfo_s *pstFrameInfo) { RtspCallbackArg_s *pstCallbackArg = (RtspCallbackArg_s *) pUserArg; MaQueSystemTime_s *pstSysTime = &pstFrameInfo->stTimeStamp.stSysTime; struct timeval stTimeVal; if (!pstCallbackArg->bClosePrint) { //DEBUG_PRINTF("<%s> Frame,Time: %ds + %dms, pts: %lld \n", // 0 == pstFrameInfo->eSubType ? "I" : "P", pstSysTime->second, // pstFrameInfo->stTimeStamp.mSec, pstFrameInfo->pts, pstCallbackArg->eStreamChn); if (MAQUE_FRAME_SUBTYPE_I == pstFrameInfo->eSubType) { DEBUG_PRINTF(" Frame, Time: %ds + %dms, pts: %lld \n", pstSysTime->second, pstFrameInfo->stTimeStamp.mSec, pstFrameInfo->pts, pstCallbackArg->eStreamChn); } } //INFO_PRINTF("eStreamChn = %d, eSubType = %d, nFrameRate = %d\n", pstCallbackArg->eStreamChn, pstFrameInfo->eSubType, pstFrameInfo->nFrameRate); stTimeVal.tv_sec = pstSysTime->day * 24 * 60 * 60 + pstSysTime->hour * 60 * 60 + pstSysTime->minute * 60 + pstSysTime->second; stTimeVal.tv_usec = pstSysTime->second * 1000; rtp_send_media(pstCallbackArg->rtspHandle, 0, pstCallbackArg->eStreamChn, (XM_S8 *)pstFrameInfo->pData, pstFrameInfo->nDataLen, &stTimeVal); MaQue_Demo_Mem_release(pstFrameInfo->handleMem); return XM_SUCCESS; } static XM_S32 Demo_Rtsp_setCameraParam(XM_VOID) { MaQueDayNightCfg_s stDncCfg; CameraModParam_s stCameraModParam = { 0 }; IRWLModParam_s stIRWLModParam = { 0 }; StringValueGet_s astCamGetValGet[] = { {"bEnabled:", &stCameraModParam.bEnabled, XM_VALUE_TYPE_INT, sizeof(stCameraModParam.bEnabled)}, {"nDemoTimeSecs:", &stCameraModParam.nDemoTimeSecs, XM_VALUE_TYPE_INT, sizeof(stCameraModParam.nDemoTimeSecs)}, {"DncMode:", &stCameraModParam.aDncMode, XM_VALUE_TYPE_STRING, sizeof(stCameraModParam.aDncMode)}, {"bIREnabled:", &stIRWLModParam.bIREnabled, XM_VALUE_TYPE_INT, sizeof(stIRWLModParam.bIREnabled)}, {"bWLEnabled:", &stIRWLModParam.bWLEnabled, XM_VALUE_TYPE_INT, sizeof(stIRWLModParam.bWLEnabled)}, }; MaQue_Demo_File_parse512(MaQue_Demo_Common_getRefFile(), "RtspCamera", astCamGetValGet, sizeof(astCamGetValGet) / sizeof(StringValueGet_s)); if (!stCameraModParam.bEnabled) { INFO_PRINTF("Camera Module Not Enabled!\n"); return XM_SUCCESS; } MaQue_Demo_Camera_ModParam_print("Demo_Rtsp_setCameraParam", &stCameraModParam); LibXmMaQue_Camera_getDayNightCfg(0, &stDncCfg); stDncCfg.eDncMode = MaQue_Demo_DncMode_str2Enum(stCameraModParam.aDncMode); LibXmMaQue_Camera_setDayNightCfg(0, &stDncCfg); if (stIRWLModParam.bWLEnabled) { LibXmMaQue_Misc_ResetLedInit(); MaQue_Demo_Common_createThread(Demo_Rtsp_ResetLed_task, NULL, "Rtsp_ResetLed"); } if (stIRWLModParam.bIREnabled) { LibXmMaQue_Camera_registerDayNightCallback(0, Demo_Rtsp_Camera_DNC_callback, NULL); } return XM_SUCCESS; } static XM_VOID *Demo_Rtsp_task(XM_VOID *pArg) { XM_S32 res; XM_U32 nTimeSecs = 0; XM_S32 bOsdInited = 0; RtspCallbackArg_s stCallbackArg[MAQUE_STREAM_CHN_NR]; rtsp_handle handleRtsp; rtsp_media_attr_t stRtspMediaAttr = { 0 }; VideoEncodeModParam_s stVidEncModParamMain = { 0 }; VideoEncodeModParam_s stVidEncModParamSec = { 0 }; VideoEncodeModParam_s stVidEncModParam = { 0 }; StringValueGet_s astVidEncValGet[] = { {"bEnabled:", &stVidEncModParam.bEnabled, XM_VALUE_TYPE_INT, sizeof(stVidEncModParam.bEnabled)}, {"bWriteFile:", &stVidEncModParam.bWriteFile, XM_VALUE_TYPE_INT, sizeof(stVidEncModParam.bWriteFile)}, {"bClosePrint:", &stVidEncModParam.bClosePrint, XM_VALUE_TYPE_INT, sizeof(stVidEncModParam.bClosePrint)}, {"nDemoTimeSecs:", &stVidEncModParam.nDemoTimeSecs, XM_VALUE_TYPE_INT, sizeof(stVidEncModParam.nDemoTimeSecs)}, {"LogoFile:", &stVidEncModParam.aLogoFile, XM_VALUE_TYPE_STRING, sizeof(stVidEncModParam.aLogoFile)}, {"CompressType:", &stVidEncModParam.aVidComp, XM_VALUE_TYPE_STRING, sizeof(stVidEncModParam.aVidComp)}, {"CaptureSize:", &stVidEncModParam.aCapSize, XM_VALUE_TYPE_STRING, sizeof(stVidEncModParam.aCapSize)}, {"BitrateCtrlType:", &stVidEncModParam.aBitrateCtrl, XM_VALUE_TYPE_STRING, sizeof(stVidEncModParam.aBitrateCtrl)}, {"ImageQuality:", &stVidEncModParam.aImgQuality, XM_VALUE_TYPE_STRING, sizeof(stVidEncModParam.aImgQuality)}, {"nFps:", &stVidEncModParam.nFps, XM_VALUE_TYPE_INT, sizeof(stVidEncModParam.nFps)}, {"nBitRate:", &stVidEncModParam.nBitRate, XM_VALUE_TYPE_INT, sizeof(stVidEncModParam.nBitRate)}, {"nIFrameInterval:", &stVidEncModParam.nIFrameInterval, XM_VALUE_TYPE_INT, sizeof(stVidEncModParam.nIFrameInterval)}, {"iQpMin:", &stVidEncModParam.iQpMin, XM_VALUE_TYPE_INT, sizeof(stVidEncModParam.iQpMin)}, {"iQpMax:", &stVidEncModParam.iQpMax, XM_VALUE_TYPE_INT, sizeof(stVidEncModParam.iQpMax)}, }; OsdTitleModParam_s stOsdTimeModParamMain = { 0 }; OsdTitleModParam_s stOsdTimeModParamSec = { 0 }; OsdTitleModParam_s stOsdTitleModParamMain = { 0 }; OsdTitleModParam_s stOsdTitleModParamSec = { 0 }; OsdTitleModParam_s stOsdTitleModParam = { 0 }; StringValueGet_s astOsdTitleValGet[] = { {"bEnabled:", &stOsdTitleModParam.bEnabled, XM_VALUE_TYPE_INT, sizeof(stOsdTitleModParam.bEnabled)}, {"Index:", &stOsdTitleModParam.stOsdParam.index, XM_VALUE_TYPE_INT, sizeof(stOsdTitleModParam.stOsdParam.index)}, {"Left:", &stOsdTitleModParam.stOsdParam.left, XM_VALUE_TYPE_INT, sizeof(stOsdTitleModParam.stOsdParam.left)}, {"Top:", &stOsdTitleModParam.stOsdParam.top, XM_VALUE_TYPE_INT, sizeof(stOsdTitleModParam.stOsdParam.top)}, {"FontSize:", &stOsdTitleModParam.stOsdParam.eFontSize, XM_VALUE_TYPE_INT, sizeof(stOsdTitleModParam.stOsdParam.eFontSize)}, {"FgTrans:", &stOsdTitleModParam.stOsdParam.fgTrans, XM_VALUE_TYPE_INT, sizeof(stOsdTitleModParam.stOsdParam.fgTrans)}, {"BgTrans:", &stOsdTitleModParam.stOsdParam.bgTrans, XM_VALUE_TYPE_INT, sizeof(stOsdTitleModParam.stOsdParam.bgTrans)}, {"FgColor:", &stOsdTitleModParam.stOsdParam.fgColor, XM_VALUE_TYPE_HEX, sizeof(stOsdTitleModParam.stOsdParam.fgColor)}, {"BgColor:", &stOsdTitleModParam.stOsdParam.bgColor, XM_VALUE_TYPE_HEX, sizeof(stOsdTitleModParam.stOsdParam.bgColor)}, {"FontLibPath:", &stOsdTitleModParam.aFontLibPath, XM_VALUE_TYPE_STRING, sizeof(stOsdTitleModParam.aFontLibPath)}, {"Title:", &stOsdTitleModParam.aTitle, XM_VALUE_TYPE_STRING, sizeof(stOsdTitleModParam.aTitle)}, }; XM_CHAR *pEnv = NULL; XM_CHAR *pFontFile = NULL; MaQue_Demo_File_parse512(MaQue_Demo_Common_getRefFile(), "RtspVideoMainChnEncode", astVidEncValGet, sizeof(astVidEncValGet) / sizeof(StringValueGet_s)); MaQue_Demo_VideoEnc_ModParam_print("Demo_Rtsp_task()