📄 raformat.cpp
字号:
m_pCommonClassFactory->CreateInstance(CLSID_IHXBuffer,
(void**) &pValue);
UINT16 uPropSize = 0;
void* pProp = m_pCodec->GetFlavorProperty(m_StreamParam.uFlavorIndex, FLV_PROP_NAME, &uPropSize);
if (uPropSize)
{
pValue->Set((const UCHAR*)pProp, uPropSize);
pRegistry->SetStrById(ulCodecRegID, pValue);
}
pValue->Release();
}
}
if (!ulCodecTextRegID)
{
// Get the current registry key name
if (!ulCodecTextRegID && (HXR_OK == pRegistry->GetPropName(ulRegistryID, pszRegistryName)))
{
SafeSprintf (szRegistryEntry, MAX_DISPLAY_NAME, "%s.CodecText", pszRegistryName->GetBuffer());
if (pParam->codecID)
{
m_pCommonClassFactory->CreateInstance(CLSID_IHXBuffer,
(void**) &pValue);
//
UINT16 uPropSize = 0;
void* pProp = m_pCodec->GetFlavorProperty(m_StreamParam.uFlavorIndex, FLV_PROP_STATUS_TEXT, &uPropSize);
if (uPropSize)
{
pValue->Set((const UCHAR*)pProp, uPropSize);
ulCodecTextRegID = pRegistry->AddStr(szRegistryEntry, pValue);
}
pValue->Release();
}
pszRegistryName->Release();
pszRegistryName = NULL;
}
}
else
{
if (pParam->codecID)
{
m_pCommonClassFactory->CreateInstance(CLSID_IHXBuffer,
(void**) &pValue);
//
UINT16 uPropSize = 0;
void* pProp = m_pCodec->GetFlavorProperty(m_StreamParam.uFlavorIndex, FLV_PROP_STATUS_TEXT, &uPropSize);
if (uPropSize)
{
pValue->Set((const UCHAR*)pProp, uPropSize);
pRegistry->SetStrById(ulCodecTextRegID, pValue);
}
pValue->Release();
}
}
if (!ulCodec4CCRegID)
{
// Get the current registry key name
if (!ulCodec4CCRegID && (HXR_OK == pRegistry->GetPropName(ulRegistryID, pszRegistryName)))
{
SafeSprintf (szRegistryEntry, MAX_DISPLAY_NAME, "%s.CodecFourCC", pszRegistryName->GetBuffer());
if (pParam->codecID)
{
m_pCommonClassFactory->CreateInstance(CLSID_IHXBuffer,
(void**) &pValue);
pValue->Set((const UCHAR*)pParam->codecID, strlen(pParam->codecID)+1);
ulCodec4CCRegID = pRegistry->AddStr(szRegistryEntry, pValue);
pValue->Release();
}
pszRegistryName->Release();
pszRegistryName = NULL;
}
}
else
{
if (pParam->codecID)
{
m_pCommonClassFactory->CreateInstance(CLSID_IHXBuffer,
(void**) &pValue);
pValue->Set((const UCHAR*)pParam->codecID, strlen(pParam->codecID)+1);
pRegistry->SetStrById(ulCodec4CCRegID, pValue);
pValue->Release();
}
}
if (!ulRateRegID || !ulChannelsRegID)
{
if (!ulRateRegID && (HXR_OK == pRegistry->GetPropName (ulRegistryID, pszRegistryName)))
{
SafeSprintf (szRegistryEntry, MAX_DISPLAY_NAME, "%s.Rate", pszRegistryName->GetBuffer());
ulRateRegID = pRegistry->AddInt (szRegistryEntry, m_IBufs.RateInBytesPerSec());
pszRegistryName->Release();
pszRegistryName = NULL;
}
if (!ulChannelsRegID && (HXR_OK == pRegistry->GetPropName (ulRegistryID, pszRegistryName)))
{
SafeSprintf (szRegistryEntry, MAX_DISPLAY_NAME, "%s.Channels", pszRegistryName->GetBuffer());
ulChannelsRegID = pRegistry->AddInt (szRegistryEntry, pParam->uChannels);
pszRegistryName->Release();
pszRegistryName = NULL;
}
}
else
{
pRegistry->SetIntById(ulRateRegID, m_IBufs.RateInBytesPerSec());
pRegistry->SetIntById(ulChannelsRegID, pParam->uChannels);
}
if (pParam->ulUserData)
{
// Get the current registry key name
if ((!ulSurroundRegID) &&
(HXR_OK == pRegistry->GetPropName(ulRegistryID, pszRegistryName)))
{
if ((pParam->ulUserData & USER_DATA_REALAUDIO_SURROUND) != 0)
{
SafeSprintf (szRegistryEntry, MAX_DISPLAY_NAME, "%s.Surround", pszRegistryName->GetBuffer());
retVal = m_pCommonClassFactory->CreateInstance(CLSID_IHXBuffer,
(void**) &pValue);
if (SUCCEEDED(retVal))
{
retVal = pValue->Set((UINT8*) "TRUE", sizeof("TRUE"));
}
if (SUCCEEDED(retVal))
{
if (ulSurroundRegID)
{
pRegistry->SetStrById(ulSurroundRegID, pValue);
}
else
{
ulSurroundRegID = pRegistry->AddStr(szRegistryEntry, pValue);
}
}
HX_RELEASE(pValue);
}
HX_RELEASE(pszRegistryName);
}
}
return retVal;
}
#endif // HELIX_FEATURE_STATS
UINT32
CRaFormat::ConvertMsToBytes(UINT32 ulMs)
{
/*
* ms # Channels * Sample size in Bits * # samples per second
* ____ * _________________________________________________________
*
* 1000 ms per second 8 bits per byte
*/
return (UINT32)(((double)(ulMs * m_StreamParam.uChannels *
m_StreamParam.uSampleSize * m_StreamParam.ulSampleRate) / 8000.0) + .5);
}
double
CRaFormat::ConvertBytesToMs(UINT32 ulBytes)
{
return (ulBytes * 8000.0) /
(m_StreamParam.uChannels *
m_StreamParam.uSampleSize *
m_StreamParam.ulSampleRate);
}
BOOL
CRaFormat::ClipAudioBuffer(HXAudioData* pAudioData,
UINT32& ulActualTime,
UINT32 ulAudioStreamTime,
BOOL bFromStart)
{
BOOL bResult = TRUE;
UINT32 ulDuration = 0;
UINT32 ulSize = 0;
INT32 lExtraInMs = 0;
UINT32 ulExtraInBytes = 0;
IHXBuffer* pBuffer = NULL;
ulSize = (pAudioData->pData)->GetSize();
// caculate the worth of this data in ms
ulDuration = (UINT32) ConvertBytesToMs(ulSize);
// trim off any extra bytes
if (bFromStart)
{
if (IsTimeGreater(pAudioData->ulAudioTime + ulDuration, ulAudioStreamTime))
{
lExtraInMs = ulAudioStreamTime - pAudioData->ulAudioTime;
}
}
else
{
if (IsTimeLess(pAudioData->ulAudioTime, ulAudioStreamTime))
{
lExtraInMs = pAudioData->ulAudioTime + ulDuration - ulAudioStreamTime;
}
}
if (lExtraInMs > 0)
{
bResult = ClipAudioData(*pAudioData,
ulActualTime,
(ULONG32) lExtraInMs,
bFromStart);
}
else if (lExtraInMs < 0)
{
// Nothing to clip
bResult = TRUE;
}
return bResult;
}
void
CRaFormat::OverrideFactory(IHXCommonClassFactory* pCommonClassFactory)
{
// Actually, we no longer override, we just add this one.
m_pCachingClassFactory = pCommonClassFactory;
m_pCachingClassFactory->AddRef();
}
BOOL
CRaFormat::GetDropBlock(UINT32 ulAudioTime)
{
BOOL bRetVal = FALSE;
if (m_bForceStartTrackTime && IsTimeLess(ulAudioTime, m_ulTrackStartTime) ||
m_ulForceDiscardUntilTime != NO_TIME_SET && IsTimeLess(ulAudioTime, m_ulForceDiscardUntilTime))
{
// since the crossfade end time is going to happen in the middle of a stream
// it has "precidence" over the track start time here
UINT32 ulStartTimeToUse = (m_ulForceDiscardUntilTime != NO_TIME_SET)?(m_ulForceDiscardUntilTime):
(m_ulTrackStartTime);
bRetVal = IsTimeLessOrEqual(ulAudioTime + (UINT32)GetMSPerBlock(), ulStartTimeToUse);
}
//XXXJEFFA add code for droping entire block clipping at end
return bRetVal;
}
void CRaFormat::SpliceAudioData(HXAudioData &audioData,
UINT32 &ulActualTimestamp,
UINT32 ulSpliceToActualTime,
UINT32 ulSpliceToStreamTime)
{
LONG32 lActualTimeDiff = 0;
ULONG32 ulAbsActualTimeDiff = 0;
audioData.uAudioStreamType = TIMED_AUDIO;
ulActualTimestamp = audioData.ulAudioTime;
if (ulSpliceToActualTime != NO_TIME_SET)
{
lActualTimeDiff = ulActualTimestamp - ulSpliceToActualTime;
ulAbsActualTimeDiff = (ULONG32) lActualTimeDiff;
if (lActualTimeDiff < 0)
{
ulAbsActualTimeDiff = (ULONG32) (-lActualTimeDiff);
}
if (ulAbsActualTimeDiff <= m_ulMaxBlockGap)
{
audioData.ulAudioTime = ulSpliceToStreamTime;
if (!m_bPCMStreamStart)
{
audioData.uAudioStreamType = STREAMING_AUDIO;
}
}
else
{
audioData.ulAudioTime = ulSpliceToStreamTime + lActualTimeDiff;
}
}
}
BOOL
CRaFormat::AdjustAudioData(HXAudioData& audioData,
UINT32& ulActualTimestamp,
UINT32 ulTrackEndTime)
{
BOOL bResult = TRUE;
UINT32 ulDuration = 0;
UINT32 ulSize = 0;
INT32 lExtraInMs = 0;
IHXBuffer* pBuffer = NULL;
if (m_bForceStartTrackTime ||
m_bForceEndTrackTime ||
(m_ulForceDiscardUntilTime != NO_TIME_SET) ||
(m_ulCrossFadeEndTime != NO_TIME_SET) ||
(ulTrackEndTime != NO_TIME_SET))
{
ulSize = (audioData.pData)->GetSize();
// caculate the worth of this data in ms
ulDuration = (UINT32) ConvertBytesToMs(ulSize);
// Trim based on start time
if (m_bForceStartTrackTime || (m_ulForceDiscardUntilTime != NO_TIME_SET))
{
// since the crossfade end time is going to happen in the middle of a stream
// it has "precidence" over the track start time here
UINT32 ulStartTimeToUse =
(m_ulForceDiscardUntilTime != NO_TIME_SET) ? m_ulForceDiscardUntilTime :
m_ulTrackStartTime;
lExtraInMs = ulStartTimeToUse - ulActualTimestamp;
bResult = ClipAndAdjust(lExtraInMs, audioData, ulActualTimestamp, TRUE, ulDuration, ulSize);
}
// Trim based on track end time
if (bResult &&
m_bForceEndTrackTime)
{
lExtraInMs = ulActualTimestamp + ulDuration - m_ulTrackEndTime;
bResult = ClipAndAdjust(lExtraInMs, audioData, ulActualTimestamp, FALSE, ulDuration, ulSize);
if (lExtraInMs > 0)
{
// if we are ending the stream here because this block goes over the forced end time
// we want to flush the IBuf etc. cause we are done.
SetupForNextTimeRange();
}
}
// Trim based on X-fade end time
if (bResult &&
(m_ulCrossFadeEndTime != NO_TIME_SET))
{
lExtraInMs = ulActualTimestamp + ulDuration - m_ulCrossFadeEndTime;
bResult = ClipAndAdjust(lExtraInMs, audioData, ulActualTimestamp, FALSE, ulDuration, ulSize);
if (lExtraInMs > 0)
{
SetupForNextTimeRange();
}
}
// Trim based on forced end time
if (bResult &&
(ulTrackEndTime != NO_TIME_SET))
{
lExtraInMs = ulActualTimestamp + ulDuration - ulTrackEndTime;
bResult = ClipAndAdjust(lExtraInMs, audioData, ulActualTimestamp, FALSE, ulDuration, ulSize);
}
}
audioData.ulAudioTime = AdjustTimestamp(audioData.ulAudioTime, m_lTimeOffset);
ulActualTimestamp = AdjustTimestamp(ulActualTimestamp, m_lTimeOffset);
return bResult;
}
BOOL
CRaFormat::ClipAudioData(HXAudioData &audioData,
UINT32 &ulActualTimestamp,
UINT32 ulDurationToClip,
BOOL bFromFront)
{
UINT32 ulExtraInBytes;
UINT32 ulSize;
BOOL bResult = FALSE; // completely elimninated = FALSE
// Get data size
ulSize = audioData.pData->GetSize();
// convert to bytes
ulExtraInBytes = ConvertMsToBytes(ulDurationToClip);
// align in sample boundary
ulExtraInBytes -= (ulExtraInBytes % (m_StreamParam.uSampleSize *
m_StreamParam.uChannels / 8));
if (ulExtraInBytes < ulSize)
{
IHXBuffer* pBuffer = NULL;
m_pCommonClassFactory->CreateInstance(CLSID_IHXBuffer,
(void**) &pBuffer);
if (pBuffer)
{
if (bFromFront)
{
if (SUCCEEDED(pBuffer->Set(audioData.pData->GetBuffer() +
ulExtraInBytes,
ulSize - ulExtraInBytes)))
{
audioData.pData->Release();
audioData.pData = pBuffer;
pBuffer = NULL;
audioData.ulAudioTime += ulDurationToClip;
ulActualTimestamp += ulDurationToClip;
bResult = TRUE;
}
}
else
{
if (SUCCEEDED(pBuffer->Set(audioData.pData->GetBuffer(),
ulSize - ulExtraInBytes)))
{
audioData.pData->Release();
audioData.pData = pBuffer;
pBuffer = NULL;
bResult = TRUE;
}
}
HX_RELEASE(pBuffer);
}
}
return bResult;
}
HX_RESULT
CRaFormat::LoadDecoderAndInitDeInterleaver()
{
HX_RESULT theError = HXR_OK;
// initialize codecs
theError = InitDecoder (m_StreamParam, &m_pCodec);
if (theError == HXR_OK)
{
// Get SAMPLES_IN from codec and give it to the IBufs
UINT16 uPropSize = 0;
void* pProp =
m_pCodec->GetFlavorProperty(m_StreamParam.uFlavorIndex,
FLV_PROP_SAMPLES_IN, &uPropSize);
if (uPropSize != 0)
{
HX_ASSERT(uPropSize == sizeof(UINT32));
m_IBufs.SetSamplesIn(*(UINT32*)pProp);
}
}
return theError;
}
BOOL CRaFormat::ClipAndAdjust(INT32 lExtraInMs,
HXAudioData& audioData,
UINT32& ulActualTimestamp,
BOOL bFromFront,
UINT32& ulDuration,
UINT32& ulSize)
{
BOOL bResult = TRUE;
if (lExtraInMs > 0)
{
bResult = ClipAudioData(audioData,
ulActualTimestamp,
(ULONG32) lExtraInMs,
bFromFront);
if (bResult)
{
ulDuration -= lExtraInMs;
ulSize = audioData.pData->GetSize();
}
else
{
ulDuration = 0;
ulSize = 0;
}
}
return bResult;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -