C#での画面キャプチャの取得方法を徹底解説!
- システム
エンジニア - 画面キャプチャについて詳しく教えてください。
- プロジェクト
マネージャー - 画面キャプチャ、もしくはスクリーンショットとも呼ばれていますね。では実際のソースコード見ながら理解を深めていきましょう。
C#での画面キャプチャについて
今回は、C#での画面キャプチャについて説明します。
スクリーン全体のキャプチャ、アクティブウィンドウのキャプチャ、矩形領域のキャプチャの方法をソースコードとともに紹介します。
C#での画面キャプチャに興味のある方はぜひご覧ください。
スクリーン全体の画面キャプチャ
C#では、スクリーン全体の画面キャプチャが取得できます。プライマリスクリーンのサイズを取得し、画面キャプチャを取得しましょう。
実際のソースコードを見てみましょう。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
|
using System;
using System.Drawing;
using System.Windows.Forms;
namespace WindowsFormsApp1
{
public partial class Form1 : Form
{
Button button1;
PictureBox pictureBox;
public Form1()
{
InitializeComponent();
this.AutoScroll = true;
this.Load += Form1_Load;
}
private void Form1_Load(object sender, EventArgs e)
{
button1 = new Button();
button1.Location = new Point(10, 10);
button1.Text = "画面全体";
button1.AutoSize = true;
button1.Click += Button1_Click;
pictureBox = new PictureBox();
pictureBox.Location = new Point(10, 40);
pictureBox.SizeMode = PictureBoxSizeMode.AutoSize;
this.Controls.Add(button1);
this.Controls.Add(pictureBox);
}
private void Button1_Click(object sender, EventArgs e)
{
// プライマリスクリーン全体
Bitmap bitmap = new Bitmap(Screen.PrimaryScreen.Bounds.Width, Screen.PrimaryScreen.Bounds.Height);
Graphics graphics = Graphics.FromImage(bitmap);
// 画面全体をコピーする
graphics.CopyFromScreen(new Point(0, 0), new Point(0, 0), bitmap.Size);
// グラフィックスの解放
graphics.Dispose();
//表示
pictureBox.Image = bitmap;
}
}
}
|
“画面全体”ボタンをクリックすると、プライマリスクリーンの画面キャプチャがFormに表示されます。
このように、C#ではスクリーン全体の画面キャプチャが取得できます。
アクティブウィンドウの画面キャプチャ
C#では、アクティブウィンドウの画面キャプチャが取得できます。
実際のソースコードを見てみましょう。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
|
using System;
using System.Drawing;
using System.Windows.Forms;
using System.Runtime.InteropServices;
namespace WindowsFormsApp1
{
public partial class Form1 : Form
{
Button button1;
PictureBox pictureBox;
[StructLayout(LayoutKind.Sequential)]
private struct Rect
{
public int left;
public int top;
public int right;
public int bottom;
}
[DllImport("user32.Dll")]
static extern int GetWindowRect(IntPtr hWnd, out Rect rect);
[DllImport("user32.dll")]
extern static IntPtr GetForegroundWindow();
public Form1()
{
InitializeComponent();
this.AutoScroll = true;
this.Load += Form1_Load;
}
private void Form1_Load(object sender, EventArgs e)
{
button1 = new Button();
button1.Location = new Point(10, 10);
button1.Text = "アクティブウィンドウ";
button1.AutoSize = true;
button1.Click += Button1_Click;
pictureBox = new PictureBox();
pictureBox.Location = new Point(10, 40);
pictureBox.SizeMode = PictureBoxSizeMode.AutoSize;
this.Controls.Add(button1);
this.Controls.Add(pictureBox);
}
private void Button1_Click(object sender, EventArgs e)
{
Rect rect;
// アクティブウィンドウを取得
IntPtr activeWindow = GetForegroundWindow();
GetWindowRect(activeWindow, out rect);
Rectangle rectangle = new Rectangle(rect.left, rect.top, rect.right - rect.left, rect.bottom - rect.top);
Bitmap bitmap = new Bitmap(rectangle.Width, rectangle.Height);
Graphics graphics = Graphics.FromImage(bitmap);
// 画面をコピー
graphics.CopyFromScreen(new Point(rectangle.X, rectangle.Y), new Point(0, 0), rectangle.Size);
// 表示
pictureBox.Image = bitmap;
}
}
}
|
“アクティブウィンドウ”ボタンをクリックすると、Form自体の画面キャプチャがFormに表示されます。
Windows Vista以降のOSの場合、Form外の領域も若干キャプチャされています。
このように、C#ではアクティブウィンドウの画面キャプチャが取得できます。
アクティブウィンドウの画面キャプチャ その2
先ほどのサンプルでは、OSによってはForm外の領域も若干キャプチャされていました。
DwmGetWindowAttributeでDWMWA_EXTENDED_FRAME_BOUNDSを指定すれば、改善できます。
実際のソースコードを見てみましょう。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
|
using System;
using System.Drawing;
using System.Windows.Forms;
using System.Runtime.InteropServices;
namespace WindowsFormsApp1
{
public partial class Form1 : Form
{
private const int SRCCOPY = 13369376;
private const int DWMWA_EXTENDED_FRAME_BOUNDS = 9;
Button button1;
PictureBox pictureBox;
[StructLayout(LayoutKind.Sequential)]
private struct Rect
{
public int left;
public int top;
public int right;
public int bottom;
}
[DllImport("user32.dll")]
static extern IntPtr GetWindowRect(IntPtr hWnd, out Rect rect);
[DllImport("user32.dll")]
extern static IntPtr GetForegroundWindow();
[DllImport("dwmapi.dll")]
extern static int DwmGetWindowAttribute(IntPtr hWnd, int dwAttribute, out Rect rect, int cbAttribute);
[DllImport("user32.dll")]
static extern IntPtr GetWindowDC(IntPtr hWnd);
[DllImport("gdi32.dll")]
static extern int BitBlt(IntPtr hDestDC, int x, int y, int nWidth, int nHeight, IntPtr hSrcDC, int xSrc, int ySrc, int dwRop);
[DllImport("user32.dll")]
static extern IntPtr ReleaseDC(IntPtr hWnd, IntPtr hdc);
public Form1()
{
InitializeComponent();
this.AutoScroll = true;
this.Load += Form1_Load;
}
private void Form1_Load(object sender, EventArgs e)
{
button1 = new Button();
button1.Location = new Point(10, 10);
button1.Text = "アクティブウィンドウ";
button1.AutoSize = true;
button1.Click += Button1_Click;
pictureBox = new PictureBox();
pictureBox.Location = new Point(10, 40);
pictureBox.SizeMode = PictureBoxSizeMode.AutoSize;
this.Controls.Add(button1);
this.Controls.Add(pictureBox);
}
private void Button1_Click(object sender, EventArgs e)
{
Rect bounds, rect;
// アクティブウィンドウを取得
IntPtr hWnd = GetForegroundWindow();
IntPtr winDC = GetWindowDC(hWnd);
DwmGetWindowAttribute(hWnd, DWMWA_EXTENDED_FRAME_BOUNDS, out bounds, Marshal.SizeOf(typeof(Rect)));
GetWindowRect(hWnd, out rect);
var offsetX = bounds.left - rect.left;
var offsetY = bounds.top - rect.top;
Bitmap bitmap = new Bitmap(bounds.right - bounds.left, bounds.bottom - bounds.top);
Graphics graphics = Graphics.FromImage(bitmap);
IntPtr hDC = graphics.GetHdc();
BitBlt(hDC, 0, 0, bitmap.Width, bitmap.Height, winDC, offsetX, offsetY, SRCCOPY);
graphics.ReleaseHdc(hDC);
graphics.Dispose();
ReleaseDC(hWnd, winDC);
// 表示
pictureBox.Image = bitmap;
}
}
}
|
“アクティブウィンドウ”ボタンをクリックすると、Form自体の画面キャプチャがFormに表示されます。
先ほどのサンプルのような、Form外の領域がキャプチャされないことが分かります。
このように、C#ではアクティブウィンドウの画面キャプチャが取得できます。
矩形領域の画面キャプチャ
C#では、矩形領域の画面キャプチャが取得できます。
実際のソースコードを見てみましょう。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
|
using System;
using System.Drawing;
using System.Windows.Forms;
namespace WindowsFormsApp1
{
public partial class Form1 : Form
{
Button button1;
PictureBox pictureBox;
public Form1()
{
InitializeComponent();
this.AutoScroll = true;
this.Load += Form1_Load;
}
private void Form1_Load(object sender, EventArgs e)
{
button1 = new Button();
button1.Location = new Point(10, 10);
button1.Text = "矩形領域";
button1.AutoSize = true;
button1.Click += Button1_Click;
pictureBox = new PictureBox();
pictureBox.Location = new Point(10, 40);
pictureBox.SizeMode = PictureBoxSizeMode.AutoSize;
this.Controls.Add(button1);
this.Controls.Add(pictureBox);
}
private void Button1_Click(object sender, EventArgs e)
{
// 矩形領域
Rectangle rectangle = new Rectangle(200, 200, 800, 500);
Bitmap bitmap = new Bitmap(rectangle.Width, rectangle.Height);
Graphics graphics = Graphics.FromImage(bitmap);
graphics.CopyFromScreen(new Point(rectangle.X, rectangle.Y), new Point(0, 0), bitmap.Size);
// グラフィックスの解放
graphics.Dispose();
//表示
pictureBox.Image = bitmap;
}
}
}
|
“矩形領域”ボタンをクリックすると、(200, 200)の座標から横800pixel、縦500pixelの矩形領域の画面キャプチャがFormに表示されます。
このように、C#では矩形領域の画面キャプチャが取得できます。
- システム
エンジニア - 画面全体の他に領域を指定した画面キャプチャ方法もあるんですね。
- プロジェクト
マネージャー - ここまで見てきたソースコードを応用して、より理解を深めていってください。
C#で画面キャプチャの取得をしよう
いかがでしたでしょうか。C#での、スクリーン全体、アクティブウィンドウ、矩形領域などの画面キャプチャ方法についてご紹介しました。
今回紹介した画面キャプチャのサンプルを応用すれば、Snipping Toolのようなアプリを作れます。
ぜひご自身でソースコードを書いて、理解を深めてみましょう。
FEnet.NETナビ・.NETコラムは株式会社オープンアップシステムが運営しています。
株式会社オープンアップシステムはこんな会社です
秋葉原オフィスには株式会社オープンアップシステムをはじめグループのIT企業が集結!
数多くのエンジニアが集まります。
-
スマホアプリから業務系システムまで
スマホアプリから業務系システムまで開発案件多数。システムエンジニア・プログラマーとしての多彩なキャリアパスがあります。
-
充実した研修制度
毎年、IT技術のトレンドや社員の要望に合わせて、カリキュラムを刷新し展開しています。社内講師の丁寧なサポートを受けながら、自分のペースで学ぶことができます。
-
資格取得を応援
スキルアップしたい社員を応援するために資格取得一時金制度を設けています。受験料(実費)と合わせて資格レベルに合わせた最大10万円の一時金も支給しています。
-
東証プライム上場企業グループ
オープンアップシステムは東証プライム上場「株式会社オープンアップグループ」のグループ企業です。
安定した経営基盤とグループ間のスムーズな連携でコロナ禍でも安定した雇用を実現させています。
株式会社オープンアップシステムに興味を持った方へ
株式会社オープンアップシステムでは、開発系エンジニア・プログラマを募集しています。
年収をアップしたい!スキルアップしたい!大手の上流案件にチャレンジしたい!
まずは話だけでも聞いてみたい場合もOK。お気軽にご登録ください。
C#新着案件New Job
-
システム開発/東京都新宿区/【WEB面談可/C#経験者/20代前半の方活躍中/経験1年以上の方活躍中】/在宅勤務
月給29万~34万円東京都新宿区(新宿駅) -
システム開発/東京都新宿区/【WEB面談可/C#経験者/20代後半~40代の方活躍中/経験年数不問】/在宅勤務
月給41万~50万円東京都新宿区(新宿駅) -
デバック、テスト項目の作成/神奈川県横浜市/【WEB面談可/C#経験者/20代前半の方活躍中/経験1年以上の方活躍中】/在宅勤務
月給29万~34万円神奈川県横浜市(桜木町駅) -
デバック、テスト項目の作成/神奈川県横浜市/【WEB面談可/C#経験者/20代後半~40代の方活躍中/経験年数不問】/在宅勤務
月給41万~50万円神奈川県横浜市(桜木町駅) -
基幹システム開発導入/東京都新宿区/【WEB面談可/C#経験者/20代前半の方活躍中/経験1年以上の方活躍中】/在宅勤務
月給29万~34万円東京都新宿区(西新宿駅) -
基幹システム開発導入/東京都新宿区/【WEB面談可/C#経験者/20代後半~40代の方活躍中/経験年数不問】/在宅勤務
月給41万~50万円東京都新宿区(西新宿駅)