⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 vncdesktopthread.cpp

📁 teamviewer source code vc++
💻 CPP
📖 第 1 页 / 共 3 页
字号:
					if (m_desktop->m_server->PollFullScreen())
					{
						if (
							(
							 //(lTime - m_lLastUpdateTime > 33) // 30 FPS max // Now Useless with RDV timing above...
							 // && 
							 (lTime - m_lLastMouseMoveTime > 100) // 100 ms pause after a Mouse move 
							) 
						    //||
						    //!m_desktop->m_server->TurboMode() // Only block FS Polling in Turbo Mode...
						   )
						{
   							m_lLastUpdateTime = lTime;
							
							if (
								(lTime - m_lLastMouseMoveTime > 300) // Restart FS Polling 300ms after last mouse move
								//|| 
								//(!m_desktop->m_server->TurboMode())
//								||
//								(!m_desktop->RestartDriver)
							   )
							   m_desktop->FastDetectChanges(rgncache, m_desktop->GetSize(), 0, true);
						}
					}
						
					
					if (m_desktop->m_server->PollForeground())
					{
						// Get the window rectangle for the currently selected window
						HWND hwnd = GetForegroundWindow();
						if (hwnd != NULL)
							 PollWindow(rgncache, hwnd);
						
					}
					
					if (m_desktop->m_server->PollUnderCursor())
					{
						// Find the mouse position
						POINT mousepos;
						if (GetCursorPos(&mousepos))
						{
							// Find the window under the mouse
							HWND hwnd = WindowFromPoint(mousepos);
							if (hwnd != NULL)
								 PollWindow(rgncache, hwnd);

						}
					}
				}
				//****************************************************************************
				//************* driver  No polling
				//****************************************************************************
				else 
				{
					// long lTime = timeGetTime();
					if (cursormoved)
					{
						// if (lTime - m_desktop->m_lLastMouseUpdateTime < 200)
						// 	continue;
						m_desktop->m_buffer.SetAccuracy(m_desktop->m_server->TurboMode() ? 2 : 1);
						// m_desktop->m_lLastMouseUpdateTime = lTime;
					}
					else
						// 4 is not that bad...but not perfect (especially with tree branchs display)
						m_desktop->m_buffer.SetAccuracy(m_desktop->m_server->TurboMode() ? 4 : 2); 
				}
				
				
				// PROCESS THE MOUSE POINTER
				// Some of the hard work is done in clients, some here
				// This code fetches the desktop under the old pointer position
				// but the client is responsible for actually encoding and sending
				// it when required.
				// This code also renders the pointer and saves the rendered position
				// Clients include this when rendering updates.
				// The code is complicated in this way because we wish to avoid 
				// rendering parts of the screen the mouse moved through between
				// client updates, since in practice they will probably not have changed.
			
				if (cursormoved && !m_desktop->m_hookdriver)
					{
						if (!m_desktop->m_cursorpos.is_empty())
						{
							// Cursor position seems to be outsite the bounding
							// When you make the screen smaller
							// add extra check
							rfb::Rect rect;
							int x = m_desktop->m_cursorpos.tl.x;
							int w = m_desktop->m_cursorpos.br.x-x;
							int y = m_desktop->m_cursorpos.tl.y;
							int h = m_desktop->m_cursorpos.br.y-y;
							if (ClipRect(&x, &y, &w, &h, m_desktop->m_bmrect.tl.x, m_desktop->m_bmrect.tl.y,
								m_desktop->m_bmrect.br.x-m_desktop->m_bmrect.tl.x, m_desktop->m_bmrect.br.y-m_desktop->m_bmrect.tl.y))
								{
									rect.tl.x = x;
									rect.br.x = x+w;
									rect.tl.y = y;
									rect.br.y = y+h;
									rgncache = rgncache.union_(rect);
//									vnclog.Print(LL_INTINFO, VNCLOG("6 %i %i %i %i "),m_desktop->m_cursorpos.br.x,m_desktop->m_cursorpos.br.y,m_desktop->m_cursorpos.tl.x,m_desktop->m_cursorpos.tl.y);
//									vnclog.Print(LL_INTINFO, VNCLOG("6 %i %i %i %i "),rect.br.x,rect.br.y,rect.tl.x,rect.tl.y);
								}
						}

					}
				

				{
					// Prevent any clients from accessing the Buffer
					omni_mutex_lock l(m_desktop->m_update_lock);
					
					// CHECK FOR COPYRECTS
					// This actually just checks where the Foreground window is
					if (!m_desktop->m_hookdriver && !m_server->SingleWindow()) 
						m_desktop->CalcCopyRects(updates);
					
					// GRAB THE DISPLAY
					// Fetch data from the display to our display cache.
					// Update the scaled rects when using server side scaling
					// something wrong inithooking again
					// We make sure no updates are in the regions
					// sf@2002 - Added "&& m_desktop->m_hookdriver"
					// Otherwise we're still getting driver updates (from shared memory buffer)
					// after a m_hookdriver switching from on to off 
					// (and m_hookdll from off to on) that causes mouse cursor garbage,
					// or missing mouse cursor.
					if (m_desktop->VideoBuffer() && m_desktop->m_hookdriver)
						{
							m_desktop->m_buffer.GrabRegion(rgncache,true);
						}
					else
						{
							m_desktop->m_buffer.GrabRegion(rgncache,false);
						}
						
					// sf@2002 - v1.1.x - Mouse handling
					// If one client, send cursor shapes only when the cursor changes.
					// This is Disabled for now.
					if( !XRichCursorEnabled==m_desktop->m_server->IsXRichCursorEnabled())
						{
							XRichCursorEnabled=m_desktop->m_server->IsXRichCursorEnabled();
							if (m_desktop->m_videodriver)
									{
											if (!XRichCursorEnabled) m_desktop->m_videodriver->HardwareCursor();
											else m_desktop->m_videodriver->NoHardwareCursor();
									}

						}
					if (m_desktop->m_server->IsXRichCursorEnabled() && !m_desktop->m_UltraEncoder_used)
						{
							if (m_desktop->m_hcursor != m_desktop->m_hOldcursor || m_desktop->m_buffer.IsShapeCleared())
									{
											m_desktop->m_hOldcursor = m_desktop->m_hcursor;
											m_desktop->m_buffer.SetCursorPending(TRUE);
											if (!m_desktop->m_hookdriver) m_desktop->m_buffer.GrabMouse(); // Grab mouse cursor in all cases
											m_desktop->m_server->UpdateMouse();
											rfb::Rect rect;
											int x = m_desktop->m_cursorpos.tl.x;
											int w = m_desktop->m_cursorpos.br.x-x;
											int y = m_desktop->m_cursorpos.tl.y;
											int h = m_desktop->m_cursorpos.br.y-y;
											if (ClipRect(&x, &y, &w, &h, m_desktop->m_bmrect.tl.x, m_desktop->m_bmrect.tl.y,
												m_desktop->m_bmrect.br.x-m_desktop->m_bmrect.tl.x, m_desktop->m_bmrect.br.y-m_desktop->m_bmrect.tl.y))
													{
														rect.tl.x = x;
														rect.br.x = x+w;
														rect.tl.y = y;
														rect.br.y = y+h;
														rgncache = rgncache.union_(rect);
//														vnclog.Print(LL_INTINFO, VNCLOG("7 %i %i %i %i "),m_desktop->m_cursorpos.br.x,m_desktop->m_cursorpos.br.y,m_desktop->m_cursorpos.tl.x,m_desktop->m_cursorpos.tl.y);
//														vnclog.Print(LL_INTINFO, VNCLOG("6 %i %i %i %i "),rect.br.x,rect.br.y,rect.tl.x,rect.tl.y);
													}
											m_server->UpdateCursorShape();
										}
						}
					else if (!m_desktop->m_hookdriver)// If several clients, send them all the mouse updates
						{
							// Render the mouse
							//if (!m_desktop->VideoBuffer())
							m_desktop->m_buffer.GrabMouse();
							
							if (cursormoved /*&& !m_desktop->m_buffer.IsCursorUpdatePending()*/) 
										{
											// Inform clients that it has moved
											m_desktop->m_server->UpdateMouse();
											// Get the buffer to fetch the pointer bitmap
											if (!m_desktop->m_cursorpos.is_empty())
											{
												rfb::Rect rect;
											int x = m_desktop->m_cursorpos.tl.x;
											int w = m_desktop->m_cursorpos.br.x-x;
											int y = m_desktop->m_cursorpos.tl.y;
											int h = m_desktop->m_cursorpos.br.y-y;
											if (ClipRect(&x, &y, &w, &h, m_desktop->m_bmrect.tl.x, m_desktop->m_bmrect.tl.y,
												m_desktop->m_bmrect.br.x-m_desktop->m_bmrect.tl.x, m_desktop->m_bmrect.br.y-m_desktop->m_bmrect.tl.y))
													{
														rect.tl.x = x;
														rect.br.x = x+w;
														rect.tl.y = y;
														rect.br.y = y+h;
														rgncache = rgncache.union_(rect);
														//vnclog.Print(LL_INTINFO, VNCLOG("8 %i %i %i %i "),m_desktop->m_cursorpos.br.x,m_desktop->m_cursorpos.br.y,m_desktop->m_cursorpos.tl.x,m_desktop->m_cursorpos.tl.y);
														//vnclog.Print(LL_INTINFO, VNCLOG("8 %i %i %i %i "),rect.br.x,rect.br.y,rect.tl.x,rect.tl.y);
													}
											}

										}
							}	
					
						
					// SCAN THE CHANGED REGION FOR ACTUAL CHANGES
					// The hooks return hints as to areas that may have changed.
					// We check the suggested areas, and just send the ones that
					// have actually changed.
					// Note that we deliberately don't check the copyrect destination
					// here, to reduce the overhead & the likelihood of corrupting the
					// backbuffer contents.
					rfb::Region2D checkrgn;
					rfb::Region2D changedrgn;
					rfb::Region2D cachedrgn;

						
					//Update the backbuffer for the copyrect region
					if (!clipped_updates.get_copied_region().is_empty()) 
						{
							rfb::UpdateInfo update_info;
							rfb::RectVector::const_iterator i;
							clipped_updates.get_update(update_info);
							if (!update_info.copied.empty()) 
								{
									for (i=update_info.copied.begin(); i!=update_info.copied.end(); i++) 						
										m_desktop->m_buffer.CopyRect(*i, update_info.copy_delta);
								}
						}
					//Remove the copyrect region from the other updates					
					//checkrgn = rgncache.union_(clipped_updates.get_copied_region());	
					checkrgn = rgncache.subtract(clipped_updates.get_copied_region());	
					//make sure the copyrect is checked next update
					rgncache = clipped_updates.get_copied_region();
					//Check all regions for changed and cached parts
					//This is very cpu intensive, only check once for all viewers
					if (!checkrgn.is_empty())
						m_desktop->m_buffer.CheckRegion(changedrgn,cachedrgn, checkrgn);

					updates.add_changed(changedrgn);
					updates.add_cached(cachedrgn);
							
					clipped_updates.get_update(m_server->GetUpdateTracker());
				}  // end mutex lock

				// Clear the update tracker and region cache an solid
				clipped_updates.clear();
				// screen blanking
				if (m_desktop->OldPowerOffTimeout!=0)
					{
					if (!m_server->BlackAlphaBlending())
						{
							SystemParametersInfo(SPI_SETPOWEROFFACTIVE, 1, NULL, 0);
							SendMessage(m_desktop->m_hwnd,WM_SYSCOMMAND,SC_MONITORPOWER,(LPARAM)2);
							//call a more administrative function to block input
							m_desktop->BlockInput(true);
							
						}
					}
			}

			
			// Now wait for more messages to be queued
			if (!WaitMessage())
			{
				vnclog.Print(LL_INTERR, VNCLOG("WaitMessage() failed"));
				break;
			}
		}//peek message


		else if (msg.message == RFB_SCREEN_UPDATE)
		{
			// Process an incoming update event
			// An area of the screen has changed
			// ddihook also use RFB_SCREEN_UPDATE
			// to passe the updates
			rfb::Rect rect;
			rect.tl = rfb::Point((SHORT)LOWORD(msg.wParam), (SHORT)HIWORD(msg.wParam));
			rect.br = rfb::Point((SHORT)LOWORD(msg.lParam), (SHORT)HIWORD(msg.lParam));
			//Buffer coordinates
			rect.tl.x-=m_desktop->m_ScreenOffsetx;
			rect.br.x-=m_desktop->m_ScreenOffsetx;
			rect.tl.y-=m_desktop->m_ScreenOffsety;
			rect.br.y-=m_desktop->m_ScreenOffsety;
//			vnclog.Print(LL_INTERR, VNCLOG("REct %i %i %i %i  "),rect.tl.x,rect.br.x,rect.tl.y,rect.br.y);
			
			rect = rect.intersect(m_desktop->m_Cliprect);
			if (!rect.is_empty())
			{
				rgncache = rgncache.union_(rect);
			}
			idle_skip = TRUE;
		}
		else if (msg.message == RFB_MOUSE_UPDATE)
		{
			// Process an incoming mouse event
			// Save the cursor ID
			m_desktop->SetCursor((HCURSOR) msg.wParam);
			idle_skip = TRUE;
		}
		else if (msg.message == RFB_KEY)
		{

			if(msg.wParam == VK_PAUSE)
			{
				vncClientList clients = m_server->ClientList();
				vncClientList::iterator i;
				for(i = clients.begin(); i!=clients.end(); i++)
				{
					vncClient *client = m_server->GetClient(*i);
					client->PauseConnection(!client->IsConnectionPaused());
				}
			}
		}
		else if (msg.message == WM_QUIT)
		{
			break;
		}
		else if (msg.message == WM_USER)
		{
			// driver dedected a cursor change
			if (MyGetCursorInfo)
			{
				MyCURSORINFO cinfo;
				cinfo.cbSize=sizeof(MyCURSORINFO);
				MyGetCursorInfo(&cinfo);
				m_desktop->SetCursor(cinfo.hCursor);
			}
		}
		else if (msg.message == WM_USER+2)
		{
			// Forced idle full screen update
			rgncache=rgncache.union_(m_desktop->m_Cliprect);
		}
		else
		{
			// Process any other messages normally
			TranslateMessage(&msg);
			DispatchMessage(&msg);
			idle_skip = TRUE;
		}
	}//while
#ifndef _DEBUG
	}
	catch(...)
	{
		vnclog.Print(LL_INTERR, VNCLOG("DesktopThread.CATCH"));
	}
#endif
	
	m_desktop->SetClipboardActive(FALSE);
	vnclog.Print(LL_INTINFO, VNCLOG("quitting desktop server thread"));
	
	// Clear all the hooks and close windows, etc.
	m_desktop->SetDisableInput(false);
	m_desktop->Shutdown();
	m_server->SingleWindow(false);
	
	// Clear the shift modifier keys, now that there are no remote clients
	vncKeymap::ClearShiftKeys();
	
	// Switch back into our home desktop, under NT (no effect under 9x)
	vncService::SelectHDESK(home_desktop);
	g_DesktopThread_running=false;
	HWND mywin=FindWindow("blackscreen",NULL);
	if (mywin)PostMessage(mywin,WM_CLOSE, 0, 0);
	return NULL;
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -