C# WPF 截屏功能

原理: 在屏幕的分别使用左、上、下和右四个矩形填满屏幕,在鼠标按下拖动的时候,获取鼠标拖动形成的矩形区域。松开鼠标后,将矩形区域内的屏幕保存为图片

ScreenCutWnd.xaml

<Window x:Class="Goldou_Comment_WPF.Comment.ScreenCutWnd"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:local="clr-namespace:Goldou_Comment_WPF.Comment"
        mc:Ignorable="d"
        Title="ScreenCutWnd"   Height="450" Width="800"  WindowStyle="None" AllowsTransparency="True"  Background="Transparent" >
    <Canvas x:Name="DrawingBoard" MouseLeftButtonDown="DrawingBoard_MouseLeftButtonDown" MouseLeftButtonUp="DrawingBoard_MouseLeftButtonUp" MouseMove="DrawingBoard_MouseMove"  >
        <Rectangle x:Name="rectangleLeft"  Fill="Black" Opacity="0.3"></Rectangle>
        <Rectangle x:Name="rectangleTop"  Fill="Black" Opacity="0.3"></Rectangle>
        <Rectangle x:Name="rectangleRight"  Fill="Black" Opacity="0.3"></Rectangle>
        <Rectangle x:Name="rectangleBottom"  Fill="Black" Opacity="0.3"></Rectangle>
        <Border x:Name="ScreenBorder" BorderBrush="LightGreen" Visibility="Hidden" BorderThickness="0.25"  ></Border>
        <WrapPanel x:Name="WrapPanelBtn" Visibility="Hidden">
            <Button x:Name="SaveBtn" Style="{StaticResource ButtonSuccess}" Margin="0,0,10,0" Content="保存" Click="Btn_Click"></Button>
            <Button x:Name="CancelBtn" Style="{StaticResource ButtonDanger}" Content="取消" Click="Btn_Click"></Button>
        </WrapPanel>
    </Canvas>
</Window>

  ScreenCutWnd.xaml.cs

using System;
using System.Collections.Generic;
using System.Drawing.Drawing2D;
using System.Drawing.Text;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Shapes;

namespace Goldou_Comment_WPF.Comment
{

    /// <summary>
    /// ScreenCutWnd.xaml 的交互逻辑
    /// </summary>
    public partial class ScreenCutWnd : Window
    {  
        private Rect rect;
        private Point pointStart, pointEnd;
        private bool isMouseUp = false;
        private bool IsFullScreen = false; //是否是截的全屏
        public ScreenCutWnd()
        {
            InitializeComponent();
            try
            {
                this.Left = 0;
                this.Top = 0;
                this.Width = SystemParameters.PrimaryScreenWidth;
                this.Height = SystemParameters.PrimaryScreenHeight;
                this.DrawingBoard.Width = SystemParameters.PrimaryScreenWidth;
                this.DrawingBoard.Height = SystemParameters.PrimaryScreenHeight;
                this.DrawingBoard.Background = new ImageBrush(tools.ChangeBitmapToImageSource(CaptureScreen()));
                rectangleLeft.Height = this.Height;
                rectangleLeft.Width = this.Width;
            }
            catch (Exception ex)
            {
                WriteLog.WriteErrorInfo(ex);
            }
        }


        private void DrawingBoard_MouseLeftButtonDown(object sender, MouseButtonEventArgs e)
        {
            try
            {
                if (!isMouseUp)
                {
                    if (ScreenBorder.Visibility == Visibility.Visible)
                    {
                        ScreenBorder.Visibility = Visibility.Hidden;
                    }
                    pointStart = e.GetPosition(DrawingBoard);
                    pointEnd = pointStart;
                    rect = new Rect(pointStart, pointEnd);
                }
            }
            catch (Exception ex)
            {
                WriteLog.WriteErrorInfo(ex);
            }
            e.Handled = true;
        }

        private void DrawingBoard_MouseLeftButtonUp(object sender, MouseButtonEventArgs e)
        {
            try
            {
                if (rect.Width + 2 >= this.Width&& rect.Height + 2 >= this.Height)
                {
                    IsFullScreen = true;
                }
                else
                {
                    IsFullScreen = false;
                }
                if (!isMouseUp && rect.Width > 0 && rect.Height > 0)
                {
                    WrapPanelBtn.Visibility = Visibility.Visible;
                    if (rect.Width+2>= this.Width)
                    {
                        Canvas.SetLeft(this.WrapPanelBtn, rect.Width - this.WrapPanelBtn.ActualWidth);
                    }
                    if (rect.Height+2>= this.Height)
                    {
                        Canvas.SetTop(this.WrapPanelBtn, rect.Height - this.WrapPanelBtn.ActualHeight);
                    }
                    else
                    {
                        Canvas.SetLeft(this.WrapPanelBtn, rect.X + rect.Width - this.WrapPanelBtn.ActualWidth);
                        Canvas.SetTop(this.WrapPanelBtn, rect.Y + rect.Height + 4);
                    }
                    isMouseUp = true;
                }
            }
            catch (Exception ex)
            {
                WriteLog.WriteErrorInfo(ex);
            }
            e.Handled = true;
        }

        private void DrawingBoard_MouseMove(object sender, MouseEventArgs e)
        {
            try
            {
                if (e.LeftButton == MouseButtonState.Pressed && !isMouseUp)
                {
                    if (ScreenBorder.Visibility != Visibility.Visible)
                    {
                        ScreenBorder.Visibility = Visibility.Visible;
                    }
                    Point current = e.GetPosition(DrawingBoard);
                    MoveAllRectangle(current);
                }
            }
            catch (Exception ex)
            {
                WriteLog.WriteErrorInfo(ex);
            }
            e.Handled = true;
        }


        protected override void OnKeyDown(KeyEventArgs e)
        {
            try
            {
                if (e.Key == Key.Escape)
                {
                    this.Close();
                }
            }
            catch (Exception ex)
            {

                WriteLog.WriteErrorInfo(ex);
            }
           
        }
    
        
      private void MoveAllRectangle(Point current)
        {
            try
            {
                pointEnd = current;
                rect = new Rect(pointStart, pointEnd);
                this.rectangleLeft.Width = rect.X;
                this.rectangleLeft.Height = DrawingBoard.Height;

                Canvas.SetLeft(this.rectangleTop, this.rectangleLeft.Width);
                this.rectangleTop.Width = rect.Width;
                double h = 0.0;
                if (current.Y < pointStart.Y)
                    h = current.Y;
                else
                    h = current.Y - rect.Height;
                this.rectangleTop.Height = h;

                Canvas.SetLeft(this.rectangleRight, this.rectangleLeft.Width + rect.Width);
                this.rectangleRight.Width = DrawingBoard.Width - (rect.Width + this.rectangleLeft.Width);
                this.rectangleRight.Height = DrawingBoard.Height;

                Canvas.SetLeft(this.rectangleBottom, this.rectangleLeft.Width);
                Canvas.SetTop(this.rectangleBottom, rect.Height + this.rectangleTop.Height);
                this.rectangleBottom.Width = rect.Width;
                this.rectangleBottom.Height = DrawingBoard.Height - (rect.Height + this.rectangleTop.Height);

                this.ScreenBorder.Height = rect.Height;
                this.ScreenBorder.Width = rect.Width;
                Canvas.SetLeft(this.ScreenBorder, rect.X);
                Canvas.SetTop(this.ScreenBorder, rect.Y);
            }
            catch (Exception ex)
            {
                WriteLog.WriteErrorInfo(ex);
            }
        }

        /// <summary>
        /// 捕获屏幕
        /// </summary>
        /// <returns></returns>
        private System.Drawing.Bitmap CaptureScreen()
        {
            var bmpCaptured = new System.Drawing.Bitmap((int)SystemParameters.PrimaryScreenWidth, (int)SystemParameters.PrimaryScreenHeight, System.Drawing.Imaging.PixelFormat.Format24bppRgb);
            using (System.Drawing.Graphics g = System.Drawing.Graphics.FromImage(bmpCaptured))
            {
                g.SmoothingMode = SmoothingMode.AntiAlias;
                g.CompositingQuality = CompositingQuality.HighQuality;
                g.InterpolationMode = InterpolationMode.HighQualityBicubic;
                g.TextRenderingHint = TextRenderingHint.ClearTypeGridFit;
                g.PixelOffsetMode = PixelOffsetMode.HighQuality;

                g.CopyFromScreen(0, 0, 0, 0, bmpCaptured.Size, System.Drawing.CopyPixelOperation.SourceCopy);
            }
            return bmpCaptured;
        }

        private void Btn_Click(object sender, RoutedEventArgs e)
        {
            try
            {
                Button button = sender as Button;
                switch (button.Name)
                {
                    case "SaveBtn":
                        if (IsFullScreen)
                        {
                            WrapPanelBtn.Visibility = Visibility.Collapsed;
                        }
                        ScreenBorder.Visibility = Visibility.Hidden;
                        BitmapEncoder pngEncoder = new PngBitmapEncoder();
                        pngEncoder.Frames.Add(BitmapFrame.Create(CutBitmap()));
                        // ImageSource 转 Bitmap
                        System.Drawing.Bitmap bitmap = tools.ImageSourceToBitmap(pngEncoder.Frames[0]);
                        // Bitmap 转 BitmapImage
                        BitmapImage bitmapImage = tools.BitmapToBitmapImage(tools.GetPicThumbnail(bitmap,800,1270));
                        //BitmapImage 转 byte[]
                        byte[] buffer = tools.BitmapImageToByteArray(bitmapImage);
                        //清理资源
                        bitmapImage.StreamSource.Close();
                        bitmapImage.StreamSource.Dispose();
                        bitmapImage = null;                 
                        //保存为文件
                       tools.SaveFile(@"E:\1.png", buffer);
                        //UDP 发送
                        UDPSend.SendScreenFile(buffer);
                        GC.Collect();
                        this.Close();
                        break;
                    case "CancelBtn":
                        this.Close();
                        break;
                    default:
                        break;
                }
            }
            catch (Exception ex)
            {
                WriteLog.WriteErrorInfo(ex);
            }
        }

      

        /// <summary>
        /// 裁剪图片
        /// </summary>
        /// <returns></returns>
        private CroppedBitmap CutBitmap()
        {
            try
            {             
                var renderTargetBitmap = new RenderTargetBitmap((int)DrawingBoard.Width, (int)DrawingBoard.Height, 96d, 96d, PixelFormats.Default);
                renderTargetBitmap.Render(DrawingBoard);           
                return new CroppedBitmap(renderTargetBitmap, new Int32Rect((int)rect.X, (int)rect.Y, (int)rect.Width, (int)rect.Height));
            }
            catch (Exception ex)
            {
                WriteLog.WriteErrorInfo(ex);
            }
            return new CroppedBitmap();
        }
    }
}

  

posted @ 2021-12-26 21:42  探索的动机  阅读(354)  评论(0编辑  收藏  举报