3

My Windows MFC application has a function to export a video file.
And it can select encoding format (via WMV or MP4) and frame size.
But, Unfortunately when i tried to export MP4 file which is set large frame size, everytime MF_E_INVALIDMEDIATYPE happened.

Simply put, here is the result when i tested in each case.

WMV

  • 640 x 480 ... OK
  • 640 x 576 ... OK
  • 1280 x 720 ... OK
  • 1280 x 720 ... OK
  • 1920 x 1080 ... OK
  • 2048 x 1556 ... OK
  • 4096 x 2160 ... OK

MP4

  • 640 x 480 ... OK
  • 640 x 576 ... OK
  • 1280 x 720 ... OK
  • 1280 x 720 ... OK
  • 1920 x 1080 ... OK
  • 2048 x 1556 ... MF_E_INVALIDMEDIATYPE
  • 4096 x 2160 ... MF_E_INVALIDMEDIATYPE

And here is my code.

HRESULT hr = S_OK;
TIFF *out;
IMFSinkWriter   *pWriter = NULL;
IMFMediaType    *pMediaTypeOut = NULL;   
IMFMediaType    *pMediaTypeIn = NULL;   
DWORD           streamIndex;     

hr = MFCreateSinkWriterFromURL(filename, NULL, NULL, &pWriter);

// Set the output media type.
if (SUCCEEDED(hr))
{
  hr = MFCreateMediaType(&pMediaTypeOut);   
}
if (SUCCEEDED(hr))
{
  hr = pMediaTypeOut->SetGUID(MF_MT_MAJOR_TYPE, MFMediaType_Video);     
}
if (SUCCEEDED(hr))
{
  if (exportMethod == ExportFormatWAV) {
    hr = pMediaTypeOut->SetGUID(MF_MT_SUBTYPE, MFVideoFormat_WVC1);
  }
  else if (exportMethod == ExportFormatMP4) {
    hr = pMediaTypeOut->SetGUID(MF_MT_SUBTYPE, MFVideoFormat_H264);   
  }
}
if (SUCCEEDED(hr))
{
  hr = pMediaTypeOut->SetUINT32(MF_MT_AVG_BITRATE, 12 * 1000 * 1000); // 12M   
}
if (SUCCEEDED(hr))
{
  hr = pMediaTypeOut->SetUINT32(MF_MT_INTERLACE_MODE, MFVideoInterlace_Progressive);   
}
if (SUCCEEDED(hr))
{
  hr = MFSetAttributeSize(pMediaTypeOut, MF_MT_FRAME_SIZE, m_width, m_height);   // e.g. 4096 x 2160
}
if (SUCCEEDED(hr))
{
  hr = MFSetAttributeRatio(pMediaTypeOut, MF_MT_FRAME_RATE, m_fps * 100, 100);   
}
if (SUCCEEDED(hr))
{
  hr = MFSetAttributeRatio(pMediaTypeOut, MF_MT_PIXEL_ASPECT_RATIO, 1, 1);   
}
if (SUCCEEDED(hr))
{
  hr = pWriter->AddStream(pMediaTypeOut, &streamIndex);   
}

// Set the input media type.
if (SUCCEEDED(hr))
{
  hr = MFCreateMediaType(&pMediaTypeIn);   
}
if (SUCCEEDED(hr))
{
  hr = pMediaTypeIn->SetGUID(MF_MT_MAJOR_TYPE, MFMediaType_Video);   
}
if (SUCCEEDED(hr))
{
  if (exportMethod == ExportFormatWAV) {
    hr = pMediaTypeIn->SetGUID(MF_MT_SUBTYPE, MFVideoFormat_RGB24);   
  }
  else if (exportMethod == ExportFormatMP4) {
    hr = pMediaTypeIn->SetGUID(MF_MT_SUBTYPE, MFVideoFormat_RGB32);     // Because H264 requires
  }
}
if (SUCCEEDED(hr))
{
  hr = pMediaTypeIn->SetUINT32(MF_MT_INTERLACE_MODE, MFVideoInterlace_Progressive);   
}
if (SUCCEEDED(hr))
{
  hr = MFSetAttributeSize(pMediaTypeIn, MF_MT_FRAME_SIZE, m_width, m_height);   // e.g. 4096 x 2160
}
if (SUCCEEDED(hr))
{
  hr = MFSetAttributeRatio(pMediaTypeIn, MF_MT_FRAME_RATE, m_fps * 100, 100);   
}
if (SUCCEEDED(hr))
{
  hr = MFSetAttributeRatio(pMediaTypeIn, MF_MT_PIXEL_ASPECT_RATIO, 1, 1);   
}
if (SUCCEEDED(hr))
{
  hr = pWriter->SetInputMediaType(streamIndex, pMediaTypeIn, NULL);   // This line returns MF_E_INVALIDMEDIATYPE
}

// Tell the sink writer to start accepting data.
if (SUCCEEDED(hr))
{
  hr = pWriter->BeginWriting();
}

I want to export a large sized video of MP4 as well.
Does anyone know a solution against this problem?

References
https://msdn.microsoft.com/en-us/library/windows/desktop/ff819477(v=vs.85).aspx
https://msdn.microsoft.com/en-us/library/windows/desktop/ff819476(v=vs.85).aspx

Oct 13th 2015

Same question has already posted msdn.
https://social.msdn.microsoft.com/Forums/en-US/ac5b71e4-e94a-4d18-bc92-8b44fa5280b6/the-max-resolution-for-mp4h264-encoder

dosuken123
  • 438
  • 3
  • 7
  • 19
  • 1
    I guess you are hitting the limits of stock H.264 encoder - in Windows 7 it is limited to Main profile and perhaps certain level, in Windows 8 the limitations are relaxed however might still be insufficient. – Roman R. Oct 09 '15 at 15:26
  • Thank you for your advice. Certainly i was testing it with Win7. But i want to make it work on Win7 as well. If i want to generate large size mp4 file in any platforms, what library should i use? – dosuken123 Oct 12 '15 at 00:59
  • 1
    There are other H.264 encoders: Intel Media SDK, libx264, MainConcept - perhaps some of them are more appropriate for your needs. The advantage of MS encoder is the fact that it's free and built into operating system. – Roman R. Oct 12 '15 at 06:16
  • Thank you very much. I'll try to use the library. – dosuken123 Oct 13 '15 at 00:24

1 Answers1

1

Media Foundation's MPEG-4 File Sink has no resolution restrictions. It multiplexes already encoded data and is not sensitive to video resolution.

If/when you, however, are encoding H.264 context, the encoders typically do have the limitations. For example, Intel(R) HD Graphics 4600's Intel® Quick Sync Video H.264 Encoder MFT can produce 4096 x 4096 H.264 content, and MP4 sink writes it correctly to file.

In your case you are likely to hit resolution limit in encoder, and since encoder rejects unsupported resolution with generic error code, you don't have anything more helpful than MF_E_INVALIDMEDIATYPE. You might have better luck with an alternate encoder.

Roman R.
  • 68,205
  • 6
  • 94
  • 158
  • By "alternate encoder", do you mean selecting a different MFT within Media Foundation? (e.g. in the case where multiple H264 encoding MFTs are installed?) If yes, how? Or do you mean switching away from Media Foundation entirely? – LTR Jan 04 '17 at 12:26
  • @LTR: Within sink writer your flexibility is to use best (hardware when available) or non-hardware (stock software) encoder only. However, you can use compression MFT outside of wink writer and feed already compressed video - sink writer will accept this to write as is. – Roman R. Jan 04 '17 at 19:09