public void UpdateCursor(ICursorStreamCodec cursorStreamCodec, int screenNumber) { var cursorInfo = new CURSORINFO(); cursorInfo.cbSize = Marshal.SizeOf(cursorInfo); if (!NativeMethods.GetCursorInfo(out cursorInfo)) { return; } if (screenNumber != _screenNumber || _screenInfo == null) { _screenNumber = screenNumber; _screenInfo = Screen.AllScreens[screenNumber]; } if (cursorInfo.hCursor != _lastCursorHandle || !cursorStreamCodec.HasCursorImage) { ICONINFO iconinfo; var cursorImage = GetCursorImage(cursorInfo, out iconinfo); if (cursorImage != null) { cursorStreamCodec.UpdateCursorImage(cursorImage); } _cursorHotspotX = iconinfo.xHotspot; _cursorHotspotY = iconinfo.yHotspot; _lastCursorHandle = cursorInfo.hCursor; Debug.Print("Update Cursor Image"); } var cursorX = cursorInfo.ptScreenPos.x - _cursorHotspotX; var cursorY = cursorInfo.ptScreenPos.y - _cursorHotspotY; var isShowing = cursorInfo.flags == CURSOR_SHOWING && _screenInfo.Bounds.Contains(cursorX, cursorY); cursorX = cursorX - _screenInfo.Bounds.X; cursorY = cursorY - _screenInfo.Bounds.Y; cursorStreamCodec.UpdateCursorInfo(cursorX, cursorY, isShowing); }
public RemoteDesktopDataInfo CaptureScreen(IStreamCodec streamCodec, ICursorStreamCodec cursorStreamCodec, bool updateCursor) { //Debug.Print("_desktopDupl == null: " + (_deskDupl == null)); if (!RetrieveFrame()) { return(null); } // Get the desktop capture texture var mapSource = _device.ImmediateContext.MapSubresource(_desktopImageTexture, 0, MapMode.Read, MapFlags.None); try { if (updateCursor) { _screenHelper.UpdateCursor(cursorStreamCodec, _currentMonitor); } #if FALSE if (updateCursor) { cursorStreamCodec.UpdateCursorInfo(_frameInfo.PointerPosition.Position.X, _frameInfo.PointerPosition.Position.Y, _frameInfo.PointerPosition.Visible); if (_frameInfo.LastMouseUpdateTime != 0 && _frameInfo.PointerShapeBufferSize > 0) { var buffer = new byte[_frameInfo.PointerShapeBufferSize]; unsafe { fixed(byte *ptrShapeBufferPtr = buffer) { int bufferSize; OutputDuplicatePointerShapeInformation shapeInfo; _deskDupl.GetFramePointerShape(_frameInfo.PointerShapeBufferSize, (IntPtr)ptrShapeBufferPtr, out bufferSize, out shapeInfo); switch (shapeInfo.Type) { case 0x1: //DXGI_OUTDUPL_POINTER_SHAPE_TYPE_MONOCHROME var size = Image.GetPixelFormatSize(PixelFormat.Format1bppIndexed); //var bitmap = new Bitmap(32, 32, 4, PixelFormat.Format1bppIndexed, (IntPtr)ptrShapeBufferPtr); cursorStreamCodec.UpdateCursorImage((IntPtr)ptrShapeBufferPtr, shapeInfo.Pitch, 32, 32, PixelFormat.Format1bppIndexed); Debug.Print("DXGI_OUTDUPL_POINTER_SHAPE_TYPE_MONOCHROME"); break; case 0x2: //DXGI_OUTDUPL_POINTER_SHAPE_TYPE_COLOR cursorStreamCodec.UpdateCursorImage((IntPtr)ptrShapeBufferPtr, shapeInfo.Pitch, shapeInfo.Width, shapeInfo.Height, PixelFormat.Format32bppArgb); Debug.Print("DXGI_OUTDUPL_POINTER_SHAPE_TYPE_COLOR"); break; case 0x4: //DXGI_OUTDUPL_POINTER_SHAPE_TYPE_MASKED_COLOR Debug.Print("DXGI_OUTDUPL_POINTER_SHAPE_TYPE_MASKED_COLOR"); break; } } } } } #endif if (_frameInfo.TotalMetadataBufferSize > 0) { int movedRegionsLength; OutputDuplicateMoveRectangle[] movedRectangles = new OutputDuplicateMoveRectangle[_frameInfo.TotalMetadataBufferSize]; _deskDupl.GetFrameMoveRects(movedRectangles.Length, movedRectangles, out movedRegionsLength); var movedRegions = new MovedRegion[movedRegionsLength / Marshal.SizeOf(typeof(OutputDuplicateMoveRectangle))]; for (int i = 0; i < movedRegions.Length; i++) { var moveRectangle = movedRectangles[i]; movedRegions[i] = new MovedRegion { Source = new Point(moveRectangle.SourcePoint.X, moveRectangle.SourcePoint.Y), Destination = new Rectangle(moveRectangle.DestinationRect.Left, moveRectangle.DestinationRect.Top, moveRectangle.DestinationRect.GetWidth(), moveRectangle.DestinationRect.GetHeight()) }; } int dirtyRegionsLength; var dirtyRectangles = new RawRectangle[_frameInfo.TotalMetadataBufferSize - movedRegionsLength]; _deskDupl.GetFrameDirtyRects(dirtyRectangles.Length, dirtyRectangles, out dirtyRegionsLength); var updatedAreas = new Rectangle[dirtyRegionsLength / Marshal.SizeOf(typeof(Rectangle))]; for (int i = 0; i < updatedAreas.Length; i++) { var dirtyRectangle = dirtyRectangles[i]; updatedAreas[i] = new Rectangle(dirtyRectangle.Left, dirtyRectangle.Top, dirtyRectangle.GetWidth(), dirtyRectangle.GetHeight()); } return(streamCodec.CodeImage(mapSource.DataPointer, updatedAreas, movedRegions, new Size(_outputDesc.DesktopBounds.GetWidth(), _outputDesc.DesktopBounds.GetHeight()), PixelFormat.Format32bppArgb)); } else { return(streamCodec.CodeImage(mapSource.DataPointer, new Rectangle(0, 0, _outputDesc.DesktopBounds.GetWidth(), _outputDesc.DesktopBounds.GetHeight()), new Size(_outputDesc.DesktopBounds.GetWidth(), _outputDesc.DesktopBounds.GetHeight()), PixelFormat.Format32bppArgb)); } } finally { _device.ImmediateContext.UnmapSubresource(_desktopImageTexture, 0); ReleaseFrame(); } }