none
VMR7 black on a secondary screen.

    Question

  • Im trying to show video using VMR7 on a secondary screen. It almost works, however when video is paused and I do this:

    I create new window on a secondary screen and use SetWindow on VMR7, it just displays black screen. Now when I move that window to a primary screen, it will show picture. When I move it back to secondary, it still displays black. When i now push play, it works. Can you  help me?

    I've tried setting monitors:

    	if (monitorConfig != null && _videoHost.WindowType == WindowTypes.Projector)
    					{
    						var monitorArray = new VMRMonitorInfo[2];
    						var devicesRead = 0;
    
    						VMRGuid monitorGuid;
    						var defaultMonitor = monitorConfig.GetDefaultMonitor(out monitorGuid);
    
    						monitorConfig.GetAvailableMonitors(monitorArray, 2, out devicesRead);
    						if (devicesRead > 0)
    						{
    							foreach (var monitorInfo in monitorArray)
    							{
    								if (monitorInfo.guid.GUID != monitorGuid.GUID)
    								{
    									//monitorConfig.SetDefaultMonitor(monitorInfo.guid);
    									monitorConfig.SetMonitor(monitorInfo.guid);
    								}
    							}
    
    						}
    					}

    It does pass SetMonitor() with a right monitor, however it does not help anything. Video is still black and only shows when I drag that window to primary window.

    What I discovered, is that flushing(CurrentPosSeconds=CurrentPosSeconds) does seem to "refresh" the "rendering contextes".

    My current solution seems to be working;

    I respond to WM_SHOWWINDOW with this:

    /// <summary>
    		/// Updates the rendering surface. Sometimes VMR7 does not play cool.
    		/// </summary>
    		private void UpdateRenderingSurface()
    		{
    			//force refresh.
    			var window = Window.GetWindow(this);
    			if (window != null)
    			{
    				window.InvalidateArrange();
    				window.InvalidateMeasure();
    				window.InvalidateVisual();
    
    				window.UpdateLayout();
    			}
    
    			//set position to same PLACE you current
    			//but this is only needed for Projector. ly are@
    			if (WindowType == WindowTypes.Projector)
    			{
    				var mediaSeeking = _graph as IMediaSeeking;
    				if (mediaSeeking != null)
    				{
    					long position = 0;
    					var hr = mediaSeeking.GetCurrentPosition(out position);
    					mediaSeeking.SetPositions(position,
    											  AMSeekingSeekingFlags.AbsolutePositioning,
    											  null,
    											  AMSeekingSeekingFlags.NoPositioning);
    				}
    			}
    		}

    You might also want to create HWND with correct cordinates right away.

    			// since VMR7 wants our renderingcontext created on a seperate window, then this is needed.
    			// hopefully this helps avoiding black window on a secondary screen problem.
    			if (windowType == WindowTypes.Projector)
    			{
    				x = (int)ViewHelper.ProjectorView.Left;
    				y = (int)ViewHelper.ProjectorView.Top;
    				width = (int)ViewHelper.ProjectorView.Width;
    				height = (int)ViewHelper.ProjectorView.Height + 20;
    			}
    
    			//automatically hidden ;)
    			//no WS_OVERLAPPEDWINDOW
    			VideoHwnd = CreateWindowEx(0, "static", "",
    						   WindowStyles.WS_CLIPCHILDREN | WindowStyles.WS_CLIPSIBLINGS,
    						  x, y,
    						  width, height,
    						  IntPtr.Zero,
    						  IntPtr.Zero,
    						  IntPtr.Zero,
    						  IntPtr.Zero);
    
    			//remove WS_BORDER.
    			const Int32 gwlStyle = (-16);
    			long style = GetWindowLong(VideoHwnd, gwlStyle);
    			style = (style & (long)~WindowStyles.WS_BORDER) | (int)WindowStyles.WS_CHILD;
    			SetWindowLong(VideoHwnd, gwlStyle, (int)style);


    C#/C++ | WPF/DirectShow/OpenGL/Winapi/




    Tuesday, November 13, 2012 9:39 AM

All replies

  • maybe u should respond to windows WM_DISPLAYCHANGE message.

    call CBaseRenderer::OnDisplayChange, see if it helps.


    Steve

    Friday, November 16, 2012 9:50 AM