メディアの種類の変換

場合によっては、Media Foundation メディアの種類と、DirectShow または Windows Media Format SDK から古いメディアの種類の構造を変換する必要があります。

書式構造から Media Foundation 型へ

次の関数は、形式構造から Media Foundation メディアの種類を初期化します。 これらの関数は、データ ストリームまたはファイル ヘッダーに書式構造が含まれている場合にも役立ちます。 たとえば、WAVE オーディオ ファイルのファイル ヘッダーには WAVEFORMATEX 構造体が含まれています。

変換する構造体 機能
AM_MEDIA_TYPE (DirectShow)
DMO_MEDIA_TYPE (DirectX メディア オブジェクト)
WM_MEDIA_TYPE (Windows Media Format SDK)
メモ: これらの構造体は同等です。
MFInitMediaTypeFromAMMediaType
BITMAPINFOHEADER MFCreateVideoMediaTypeFromBitMapInfoHeaderEx
MFVIDEOFORMAT MFInitMediaTypeFromMFVideoFormat
MPEG1VIDEOINFO MFInitMediaTypeFromMPEG1VideoInfo
MPEG2VIDEOINFO MFInitMediaTypeFromMPEG2VideoInfo
VIDEOINFOHEADER2 MFInitMediaTypeFromVideoInfoHeader2
VIDEOINFOHEADER MFInitMediaTypeFromVideoInfoHeader
WAVEFORMATEX または WAVEFORMATEXTENSIBLE MFInitMediaTypeFromWaveFormatEx

 

Media Foundation の種類から書式構造へ

次の関数は、Media Foundation メディアの種類から書式構造を作成または初期化します。

機能 ターゲット構造
IMFMediaType::GetRepresentation AM_MEDIA_TYPEMFVIDEOFORMATVIDEOINFOHEADER、または VIDEOINFOHEADER2
MFCreateAMMediaTypeFromMFMediaType AM_MEDIA_TYPE
MFCreateMFVideoFormatFromMFMediaType MFVIDEOFORMAT
MFCreateWaveFormatExFromMFMediaType WAVEFORMATEX または WAVEFORMATEXTENSIBLE
MFInitAMMediaTypeFromMFMediaType AM_MEDIA_TYPE

 

マッピングの書式設定

次の表に、さまざまな形式構造に対応する Media Foundation 属性の一覧を示します。 これらの属性の一部を直接変換できるわけではありません。 変換を実行するには、前のセクションで示した関数を使用する必要があります。これらのテーブルは、主に参照用に提供されています。

AM_MEDIA_TYPE

メンバー 属性
bTemporalCompression MF_MT_ALL_SAMPLES_INDEPENDENT
bFixedSizeSamples MF_MT_FIXED_SIZE_SAMPLES
lSampleSize MF_MT_SAMPLE_SIZE

 

WAVEFORMATEX、WAVEFORMATEXTENSIBLE

メンバー 属性
wFormatTag MF_MT_SUBTYPE
wFormatTag がWAVE_FORMAT_EXTENSIBLE場合、サブタイプは SubFormat メンバーにあります。
nChannels MF_MT_AUDIO_NUM_CHANNELS
nSamplesPerSec MF_MT_AUDIO_SAMPLES_PER_SECOND
nAvgBytesPerSec MF_MT_AUDIO_AVG_BYTES_PER_SECOND
nBlockAlign MF_MT_AUDIO_BLOCK_ALIGNMENT
wBitsPerSample MF_MT_AUDIO_BITS_PER_SAMPLE
wValidBitsPerSample MF_MT_AUDIO_VALID_BITS_PER_SAMPLE
wSamplesPerBlock MF_MT_AUDIO_SAMPLES_PER_BLOCK
dwChannelMask MF_MT_AUDIO_CHANNEL_MASK
SubFormat MF_MT_SUBTYPE
追加のデータ MF_MT_USER_DATA

 

VIDEOINFOHEADER、VIDEOINFOHEADER2

メンバー 属性
dwBitRate MF_MT_AVG_BITRATE
dwBitErrorRate MF_MT_AVG_BIT_ERROR_RATE
AvgTimePerFrame MF_MT_FRAME_RATE。この値を計算するには、 MFAverageTimePerFrameToFrameRate を使用します。
dwInterlaceFlags MF_MT_INTERLACE_MODE
dwCopyProtectFlags 同等の定義はありません
dwPictAspectRatioXdwPictAspectRatioY MF_MT_PIXEL_ASPECT_RATIO;は、画像の縦横比から図の縦横比に変換する必要があります。
dwControlFlags MF_MT_PAD_CONTROL_FLAGSAMCONTROL_COLORINFO_PRESENT フラグが存在する場合は、「拡張カラー情報」で説明されている拡張カラー属性を設定します。
bmiHeader.biWidthbmiHeader.biHeight MF_MT_FRAME_SIZE
bmiHeader.biBitCount サブタイプ (MF_MT_SUBTYPE) で暗黙的です。
bmiHeader.biCompression サブタイプの暗黙的。
bmiHeader.biSizeImage MF_MT_SAMPLE_SIZE
パレット情報 MF_MT_PALETTE

 

次の属性は VIDEOINFOHEADER または VIDEOINFOHEADER2 構造体から推論できますが、形式の詳細に関する知識も必要です。 たとえば、YUV 形式によってストライド要件が異なります。

MPEG1VIDEOINFO

メンバー 属性
dwStartTimeCode MF_MT_MPEG_START_TIME_CODE
bSequenceHeader MF_MT_MPEG_SEQUENCE_HEADER
biXPelsPerMeterbiYPelsPerMeter MF_MT_PIXEL_ASPECT_RATIO

 

MPEG2VIDEOINFO

メンバー 属性
dwStartTimeCode MF_MT_MPEG_START_TIME_CODE
dwSequenceHeader MF_MT_MPEG_SEQUENCE_HEADER
dwProfile MF_MT_MPEG2_PROFILE
dwLevel MF_MT_MPEG2_LEVEL
dwFlags MF_MT_MPEG2_FLAGS

 

次のコードは、ビデオ メディアの種類から BITMAPINFOHEADER 構造体を入力します。 この変換では、一部の形式情報 (インターレース、フレーム レート、拡張カラー データ) が失われることに注意してください。 ただし、たとえば、ビデオ フレームからビットマップを保存する場合に便利な場合があります。

#include <dshow.h>
#include <dvdmedia.h>

// Converts a video type to a BITMAPINFO structure.
// The caller must free the structure by calling CoTaskMemFree.

// Note that this conversion loses some format information, including 
// interlacing, and frame rate.

HRESULT GetBitmapInfoHeaderFromMFMediaType(
    IMFMediaType *pType,            // Pointer to the media type.
    BITMAPINFOHEADER **ppBmih,      // Receives a pointer to the structure. 
    DWORD *pcbSize)                 // Receives the size of the structure.
{
    *ppBmih = NULL;
    *pcbSize = 0;

    GUID majorType = GUID_NULL;
    AM_MEDIA_TYPE *pmt = NULL;
    DWORD cbSize = 0;
    DWORD cbOffset = 0;
    BITMAPINFOHEADER *pBMIH = NULL;

    // Verify that this is a video type.
    HRESULT hr = pType->GetMajorType(&majorType);
    if (FAILED(hr))
    {
        goto done;
    }

    if (majorType != MFMediaType_Video)
    {
        hr = MF_E_INVALIDMEDIATYPE;
        goto done;
    }

    hr = pType->GetRepresentation(AM_MEDIA_TYPE_REPRESENTATION, (void**)&pmt);
    if (FAILED(hr))
    {
        goto done;
    }

    if (pmt->formattype == FORMAT_VideoInfo)
    {
        cbOffset = (FIELD_OFFSET(VIDEOINFOHEADER,bmiHeader));
    }
    else if (pmt->formattype == FORMAT_VideoInfo2)
    {
        cbOffset = (FIELD_OFFSET(VIDEOINFOHEADER2,bmiHeader));
    }
    else
    {
        hr = MF_E_INVALIDMEDIATYPE; // Unsupported format type.
        goto done;
    }

    if (pmt->cbFormat - cbOffset < sizeof(BITMAPINFOHEADER))
    {
        hr = E_UNEXPECTED; // Bad format size. 
        goto done;
    }

    cbSize = pmt->cbFormat - cbOffset;

    pBMIH = (BITMAPINFOHEADER*)CoTaskMemAlloc(cbSize);
    if (pBMIH == NULL)
    {
        hr = E_OUTOFMEMORY;
        goto done;
    }
    
    CopyMemory(pBMIH, pmt->pbFormat + cbOffset, cbSize);
    
    *ppBmih = pBMIH;
    *pcbSize = cbSize;

done:
    if (pmt)
    {
        pType->FreeRepresentation(AM_MEDIA_TYPE_REPRESENTATION, pmt);
    }
    return hr;
}

メディアの種類