您当前的位置: 首页 > 

qianbo_insist

暂无认证

  • 0浏览

    0关注

    399博文

    0收益

  • 0浏览

    0点赞

    0打赏

    0留言

私信
关注
热门博文

程序的多显示器支持

qianbo_insist 发布时间:2021-07-14 07:15:52 ,浏览量:0

多显示器

在系统中存在多个显示器是经常碰到的情况,如果存在,在哪个显示器上执行满屏的时候,系统不能随意把执行播放或者普通显示到首个显示器中,而是应该显示在显示界面当前的显示接口中。 多个显示器 以下讨论windows下MFC的多显示器支持。

先看以下代码,MFC view的视图类中,我们使用封装类CMonitor,可以获取有多少个显示器,并且得到显示的矩形窗口

int CMFCApplication3View::MonitorMonitor(RECT &rect)
{
	int count = CMonitors::GetMonitorCount();
	if (count > 0)
	{
		CMonitor monitor = CMonitors::GetNearestMonitor(this);
		//RECT myrect;
		monitor.GetMonitorRect(&rect);
		return 0;
	}
	return -1;
}

下面是转换全屏的逻辑代码

void CMFCApplication3View::FullScreenToggle()
{
	if (m_bFullScreen)
	{
		LockWindowUpdate();
		HWND hWnd_ = GetSafeHwnd();
		::SetParent(hWnd_, m_hWndParent);
		SetWindowPlacement(&_temppl);
		::SetForegroundWindow(m_hWndParent);
		::SetFocus(m_hWndParent);
		::SetFocus(hWnd_);
		UnlockWindowUpdate();
	}
	else
	{
		
		WINDOWPLACEMENT wp1;
		ZeroMemory(&wp1, sizeof(WINDOWPLACEMENT));
		wp1.length = sizeof(WINDOWPLACEMENT);
		wp1.showCmd = SW_SHOWNORMAL;

		if (MonitorMonitor(wp1.rcNormalPosition) != 0)
		{
			int nScreenWidth = GetSystemMetrics(SM_CXSCREEN);
			int nScreenHeight = GetSystemMetrics(SM_CYSCREEN);
			wp1.rcNormalPosition.left = 0;
			wp1.rcNormalPosition.top = 0;
			wp1.rcNormalPosition.right = nScreenWidth;
			wp1.rcNormalPosition.bottom = nScreenHeight;
		}
		HWND hWnd_ = GetSafeHwnd();
		GetWindowPlacement(&_temppl);
		//GetWindowPlacement(&_temppl);
		m_hWndParent = ::GetParent(hWnd_);
		::SetParent(hWnd_, GetDesktopWindow()->m_hWnd);

		SetWindowPlacement(&wp1);
		::SetForegroundWindow(GetDesktopWindow()->m_hWnd);
		::SetForegroundWindow(hWnd_);
	}
	m_bFullScreen = !m_bFullScreen;
}

CMonitor实际上使用API函数MonitorFromWindow 来获取显示器接口。


CMonitor CMonitors::GetNearestMonitor( const CWnd* pWnd )
{
	ASSERT( pWnd );
	ASSERT( ::IsWindow( pWnd->m_hWnd ) );

	CMonitor monitor;
	monitor.Attach( ::MonitorFromWindow( pWnd->GetSafeHwnd(), MONITOR_DEFAULTTONEAREST ) );

	return monitor;
}
其他API 2.1 得到显示器信息
    MONITORINFO mi;
    RECT        rc;
	mi.cbSize = sizeof( mi );
	::GetMonitorInfo( m_hMonitor, &mi );
2.2 得到像素点信息技巧
int CMonitor::GetBitsPerPixel() const
{
	HDC hdc = CreateDC();
	int ret = ::GetDeviceCaps( hdc, BITSPIXEL ) * ::GetDeviceCaps( hdc, PLANES );
	VERIFY( ::DeleteDC( hdc ) );

	return ret;
}
2.3 是否是窗口
::IsWindow( pWnd->GetSafeHwnd() 

IsWindow 函数非常有用,在“窗口“”还没有成为窗口的时候,我们可以用这个函数作为判断,启动过程中,窗口还没有初始化完毕,我们不能使用窗口的一些特性,否则就会造成程序崩溃

2.4 设置窗口位置
 pWnd->SetWindowPos( NULL, rect.left, rect.top, 0, 0, SWP_NOSIZE | SWP_NOZORDER | SWP_NOACTIVATE );

这个其实就是关键API函数,要让界面全屏在哪个显示器上,无非就是计算整个显示区域,并设置窗口位置罢了。

总结

无论哪个操作系统的原理都是类似的,程序代码在于理解层次和逻辑,数据结构和算法,不在于哪种操作系统和哪种语言,无论是国产化操作系统和非国产化我们都要理解原理去操作,以上API和示例,希望帮助需要帮助的人。

我是协议专家,有问题可以共同探讨。按照我的博客页面首页可以找到我。

关注
打赏
1663161521
查看更多评论
立即登录/注册

微信扫码登录

0.0397s