winform屏幕截圖

屏幕截圖是一個比較經常使用的功能,在項目中出現的比例也比較高,至少我作過的每一個項目都有屏幕截圖這個功能,從全屏截圖到區域截圖都有出現過。固然區域截圖已然包含了全屏截圖。windows

全屏截圖方式有好幾種,調用API截圖、調用操做系統的截圖而後到剪切板去取(固然這種方式幾乎沒人會去用)、用Graphics去畫屏幕等等。this

下面上Graphics畫屏幕的代碼,畢竟這種方式代碼量最少。spa

            //截取屏幕
            Bitmap myImage = new Bitmap(Screen.PrimaryScreen.Bounds.Width, Screen.PrimaryScreen.Bounds.Height);
            Graphics g = Graphics.FromImage(myImage);
            g.CopyFromScreen(new Point(0, 0), new Point(0, 0), new Size(Screen.PrimaryScreen.Bounds.Width, Screen.PrimaryScreen.Bounds.Height));        
            g.Dispose();

上面的代碼便可截取當前屏幕的圖像。注:因爲WPF是使用DirectX進行渲染的,此方式截圖在部分系統會截圖不到wpf的窗體。(win7,windows server2008,windows vista均能截取到wpf窗體,windows XP沒法截取到WPF窗體,緣由多是windows xp出現時尚未WPF呢)操作系統

實現區域截圖,主要有四個步驟,一截取全屏,彈出遮罩層,畫選擇區,截取選擇區域code

1、截取全屏可用上面代碼實現,這裏就不寫了。orm

2、彈出遮罩層server

     遮罩層的目的是用來畫截圖區域,通常採用半透明方式。代碼以下:blog

            this.BackColor = Color.Gray;
            this.Opacity = 0.5;
            this.FormBorderStyle = FormBorderStyle.None;
            this.WindowState = FormWindowState.Maximized;

  設置窗體背景顏色,通明度,邊框樣式及使其最大化。便可彈出全屏遮罩層。事件

3、畫選擇區圖片

  這個就是截屏中最重要的部分了

  咱們須要在窗體中加入pictureBox控件,且Dock屬性設置爲Fill,這樣才能在屏幕上畫選擇區

跟隨鼠標在 pictureBox的圖片上畫矩形
        private int intStartX = 0;
        private int intStartY = 0;
        private bool isMouseDraw = false;
 
        private void pictureBox_Src_MouseDown(object sender, MouseEventArgs e)
        {
            isMouseDraw = true;
 
            intStartX = e.X;
            intStartY = e.Y;
        }
 
        private void pictureBox_Src_MouseMove(object sender, MouseEventArgs e)
        {
            if (isMouseDraw)
            {
                try
                {
                    Graphics g = this.pictureBox_Src.CreateGraphics();
                    //清空上次畫下的痕跡
                    g.Clear(this.pictureBox_Src.BackColor);
                    Brush brush = new SolidBrush(Color.Red);
                    Pen pen = new Pen(brush, 1);
                    pen.DashStyle = DashStyle.Solid;
                    g.DrawRectangle(pen, new Rectangle(intStartX > e.X ? e.X : intStartX, intStartY > e.Y ? e.Y : intStartY, Math.Abs(e.X - intStartX), Math.Abs(e.Y - intStartY)));
                    g.Dispose();
                }
                catch (Exception ex)
                {
                    ex.ToString();
                }
            }
        }
 
        private void pictureBox_Src_MouseUp(object sender, MouseEventArgs e)
        {
            isMouseDraw = false;
 
            intStartX = 0;
            intStartY = 0;
        }

固然這只是在圖片上畫了一個紅色的矩形,無法二次調整矩形大小,移動矩形,且畫圖時會不停的清除畫下的痕跡,致使屏幕閃爍,且平時使用的屏幕截圖在選擇區的區域亮度都會高些,這些都沒實現,不過既然能畫區域了那這些就都不是問題了,只需稍做修改便可,如下給出部分修改代碼:

填充選擇區

SolidBrush soldwhite = new SolidBrush(Color.White);
Rectangle rec = new Rectangle(StartX, StartY, ScreenWidth, ScreenHeight);

g.FillRectangle(soldwhite, rec);//用來填充矩形區域

屏幕閃爍

清除時屏幕閃爍是因爲清除的整個圖片,而後在從新繪製的,這樣若加上填充區設置爲白色,咱們能看到填充區域閃爍的很厲害,解決方式爲採用填充的方式清除選擇區域外的部分,這樣整個圖片總共分5此填充和一次劃線。

            Graphics g = this.pictureBox1.CreateGraphics();
                    //清空上次畫下的痕跡
                   // g.Clear(this.pictureBox1.BackColor);
                    g.FillRectangle(soldgray, 0, 0, pictureBox1.Width, StartY);//清除上
                    g.FillRectangle(soldgray, 0, StartY + ScreenHeight, pictureBox1.Width, pictureBox1.Height - (StartY + ScreenHeight));//清除下
                    g.FillRectangle(soldgray, 0, StartY, StartX, ScreenHeight + 1);//清除左
                    g.FillRectangle(soldgray, StartX + ScreenWidth, StartY, pictureBox1.Width - (StartX + ScreenWidth), ScreenHeight + 1);//清除右

二次調整大小及選擇區移動

當咱們對區域進行選擇後,想二次調整大小一般會看到鼠標樣式變化,表示能夠對其進行修改或移動

        /// <summary>
        /// 設置鼠標樣式
        /// </summary>
        /// <param name="p"></param>
        private void SetCursorStyle(Point p)
        {
            if (p.X > StartX && p.X < StartX + ScreenWidth && p.Y > StartY && p.Y < StartY + ScreenHeight)
            {this.Cursor = Cursors.SizeAll;
            }
            else if (p.X >= StartX - 10 && p.X <= StartX && p.Y >= StartY - 10 && p.Y <= StartY)
            {this.Cursor = Cursors.SizeNWSE;
            }
            else if (p.X >= StartX + ScreenWidth && p.X <= StartX + ScreenWidth + 10 && p.Y <= StartY + ScreenHeight + 10 && p.Y >= StartY + ScreenHeight)
            {this.Cursor = Cursors.SizeNWSE;
            }
            else if ((p.X >= StartX + ScreenWidth && p.X <= StartX + ScreenWidth + 10 && p.Y >= StartY - 10 && p.Y <= StartY))
            {this.Cursor = Cursors.SizeNESW;
            }
            else if (p.X >= StartX - 10 && p.X <= StartX && p.Y <= StartY + ScreenHeight + 10 && p.Y >= StartY + ScreenHeight)
            {this.Cursor = Cursors.SizeNESW;
            }
            else
            {this.Cursor = Cursors.Default;
            }
        }

這是設置鼠標在選擇區域內的樣式和四個角的樣式,如果在4個角,只需將起始座標設置好以後和原來同樣畫區域就行,如果在區域中,移動選擇區則需根據當前座標和開始座標計算出差值,在移動時更改開始座標,固定寬高畫區域便可,若移動到屏幕邊緣需加上判斷。

4、截取選擇區域

畫好區域後,須要選擇是否截取,一般會給出按鈕選擇咱們只需在MouseUP和MouseDown事件中加上按鈕的隱藏和顯示便可,顯示時根據選擇區計算顯示的座標位置。

截取選擇區代碼

Bitmap map = myImage.Clone(new Rectangle(StartX, StartY, ScreenWidth, ScreenHeight), System.Drawing.Imaging.PixelFormat.Format32bppArgb);

這樣便可實現簡單的區域截圖了。

相關文章
相關標籤/搜索