Reputation: 3574
I have a C#
application which plays videos using the DirectShowNet
library. When I debug my application using Visual C# on my laptop, the video is stretched to fit the container's dimensions i.e. the aspect ratio of the video is not maintained. When I load and run my application on a different computer (same operating system), the aspect ratio
is maintained and black bars are created on the screen.
I do not want the aspect ratio to be maintained. I want the other computer to display the video the same way my computer is displaying it.
Why do you think the two computer's act differently and/or how do I fix this?
When I first saw this behaviour on the other computer, I updated that computer's DirectX
to no avail. The exact same videos are being run on both systems.
EDIT #1: Could it possibly be some missing filter
on the other computer? I assumed the default behaviour of DirectShow
was not to maintain the Aspect Ratio
.
EDIT #2: When I attempted to use IVMRWindowlessControl
(VMR-7
& VMR-9
), the cast from the VMR to the IVMRWindowlessControl
kept on resulting in a NULL
variable. As a result I tried IVMRAspectRatioControl
with VMR-7
and it worked on one of the computers. The other computer stayed in Letterbox mode despite the call to remove the Aspect Ratio preservation.
EDIT #3: Here is the code using IVMRAspectRatioControl
with VMR-7
:
int hr = 0;
this.graphBuilder = (IGraphBuilder)new FilterGraph();
this.vmr = new VideoMixingRenderer();
this.graphBuilder.AddFilter((IBaseFilter)vmr, "VMR");
this.aspectRatioControl = (IVMRAspectRatioControl)this.vmr;
hr = this.aspectRatioControl.SetAspectRatioMode(VMRAspectRatioMode.None);
DsError.ThrowExceptionForHR(hr);
hr = this.graphBuilder.RenderFile(filename, null);
DsError.ThrowExceptionForHR(hr);
I am then using IVideoWindow
to display the video.
When attempting to use the IVMRWindowlessControl9
, the this.windowlessControl
evaluated to NULL
after the cast
on the 4th line. I get the same NULL
error when I tried it with VMR-7
. The following uses VMR-9
:
this.graphBuilder = (IGraphBuilder)new FilterGraph();
this.vmr = new VideoMixingRenderer9();
this.graphBuilder.AddFilter((IBaseFilter)vmr, "VMR");
this.filterConfig = (IVMRFilterConfig9)vmr;
hr = this.filterConfig.SetNumberOfStreams(1);
DsError.ThrowExceptionForHR(hr);
hr = this.filterConfig.SetRenderingMode(VMR9Mode.Windowless);
DsError.ThrowExceptionForHR(hr);
this.windowlessControl = (IVMRWindowlessControl9)this.vmr;
hr = this.windowlessControl.SetAspectRatioMode(VMR9AspectRatioMode.None);
DsError.ThrowExceptionForHR(hr);
hr = this.graphBuilder.RenderFile(filename, null);
DsError.ThrowExceptionForHR(hr);
I'm not entirely sure how it works, but could it be possible that the second computer does not support VMR-7
for the IVMRAspectRatioControl
? The operating systems on both computers are the same, however the first computer (which works) is where I'm writing the software (it has the IDE). The second computer had a fresh install of Windows
. On the second computer, I also updated DirectX
as mentioned earlier.
Upvotes: 0
Views: 1270
Reputation: 69662
Video renderers can be configured to preserve or not preserve aspect ratio. Configuration method (and, perhaps, default setting, which can also depend on internal mode of the renderer such as overlay/offscreen surface) is dependent on video renderer version you are using, e.g. for VMR-7 you will use IVMRWindowlessControl::SetAspectRatioMode
's (or, IVMRAspectRatioControl::SetAspectRatioMode
if your VMR is in windowed mode) DirectShow.NET equivalent/wrapper. VMR-9, EVR has similar methods.
With VMR-9 you will use IVMRAspectRatioControl9::SetAspectRatioMode
. With EVR it is IMFVideoDisplayControl::SetAspectRatioMode
.
If you don't want any letterboxing and aspect ration preservation, you just disable it explicitly when you set the video renderer up.
Upvotes: 2