[C++/CLI] モニタの解像度をプログラムから変更する

たまに C++/CLI の記事などを。Visual Studio 2012 からは C++/CLI もインテリセンスが使えるようになったので、C# と win api を媒介する C++/CLI のプログラミングもばっちりですね…って、2010 の時に出してほしかったよなぁ。ちなみに、2012 では C++/CLI でフォームアプリケーションが作れない(ことはないけど、テンプレートに入っていない)ので、そのままフェイドアウト…なのか? それとも C++/CX と融合するのかは謎なところです。

■解像度とモニタを指定する

解像度自体は、ChangeDisplaySettingsEx 関数を使いますが、複数のモニタがある場合はデバイス名が必要にあんるので、あらかじめ EnumDisplayDevices で取得しておきます。
本来は、モニタのリストとかを取ればいいのですが、画面キャプチャ用のツールなので、モニタ数などは決め打ちで。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
#include <windows.h>
#include <WinUser.h>
 
public ref class GDI
{
public:
    static void ChangeDisplay( int width, int height, int moniter )
    {
        // デバイス名の取得
        DISPLAY_DEVICE disp;
        EnumDisplayDevices( NULL, moniter, &disp, NULL );
        // 解像度を設定
        DEVMODE mode = {0};
        mode.dmSize = sizeof(mode);
        mode.dmPelsWidth = width ;
        mode.dmPelsHeight = height ;
        mode.dmFields = DM_PELSWIDTH|DM_PELSHEIGHT;
        // 解像度を変更
        long ret = ChangeDisplaySettingsEx( disp.DeviceName, &mode, NULL, 0, NULL );
    }
};

■C# から呼び出す

画面自体は、C# で作ります。
解像度自体は、コントローパネルから調べて決め打ちです。ボタン一発で切り替えることができます。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
/// <summary>
/// 解像度変更
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
private void button10_Click(object sender, EventArgs e)
{
    scrcaplib.GDI.ChangeDisplay(1024, 768, 1);
}
/// <summary>
/// 解像度変更
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
private void button11_Click(object sender, EventArgs e)
{
    scrcaplib.GDI.ChangeDisplay(1280, 1024, 1);
}

これを C# だけでやろうとすると、構造体やら定数定義やらがややこしいんですよね。なので、win api を直接叩くのではなく、C++/CLI を媒介にすると簡単になるよ、という実例です。

カテゴリー: C#, C++ パーマリンク