2010/02/27(土)画面の解像度を変える

はてブ数 2010/02/27 14:01 プログラミング::HSP3つーさ

chgdisp は終了すると戻っちゃうので、というわけでサクっと作った。

僕のマシンには、PATHの通った場所にいくつか簡単なアプリを置いてます。

  • 1920.exe 画面解像度を 1920x1080 に変更して終了するだけのアプリ
  • 1280.exe 画面解像度を 1280x1024 に変更して終了するだけのアプリ
  • 1024.exe 画面解像度を 1024x768 に変更して終了するだけのアプリ
  • 800.exe 画面解像度を 800x600 に変更して終了するだけのアプリ
  • 640.exe 画面解像度を 640x480 に変更して終了するだけのアプリ

これを、Win+R のファイル名を指定して実行 から呼び出すわけです。
地味に便利です(特に遠隔地からVNCしてるとき)。
しかし、API呼ぶだけのアプリとかCのがラクすぎるだろ……と思った(今はCから移植した)。

モジュールは好きに使ってください
フツーに誰か作ってそうだなこれ。

#module
#uselib "user32.dll"
#func ChangeDisplaySettingsEx "ChangeDisplaySettingsExA" int, int, int, int, int

// ディスプレイモードの変更を試みる
  // w = 幅 => -1:全リセット 0:このパラメータを無視
  // h = 高さ
  // bpp = ビット数 => 0:このパラメータを無視
  // rhz = リフレッシュレート => 0:このパラメータを無視
  // flags = フラグ => 1:レジストリも変更 2:テストのみ
  // 戻り値 = 0:成功 1:再起動が必要 それ以外:失敗
#deffunc TryChangeDisplayMode int w, int h, int bpp, int rhz, int flags, local devmode

  // レジストリ値でリセット
  if w == -1 : ChangeDisplaySettingsEx 0, 0, 0, 0, 0 : return stat

  // DEVMODE 構造体の準備
  dim devmode, 39 : devmode.9 = 156 /* = sizeof(DEVMODE) */

  devmode.26 = bpp /* dmBitsPerPel */
  devmode.27 = w /* dmPelsWidth */
  devmode.28 = h /* dmPelsHeight */
  devmode.30 = rhz /* dmPelsHeight */

  if w : devmode.10 |= 0x0018000 /* LDM_PELSWIDTH | DM_PELSHEIGHT */
  if rhz : devmode.10 |= 0x00400000 /* DM_DISPLAYFREQUENCY */
  if bpp : devmode.10 |= 0x0004000 /* DM_BITSPERPEL */

  // CDS_TEST 付きで変更できるかテスト
  ChangeDisplaySettingsEx 0, varptr(devmode), 0, 2 /* CDS_TEST */, 0
  if stat ! 0 : return stat // 無理

  // 実際に変更
  ChangeDisplaySettingsEx 0, varptr(devmode), 0, flags, 0
  return stat

// chgdispの代替。 updateRegistry に 1を指定するとレジストリにも保存
#deffunc chgdisp2 int mode, int w, int h, int updateRegistry
  switch mode
    case 0:
      TryChangeDisplayMode -1 : if stat = 0 : return 0
      return 2
    case 1:
      TryChangeDisplayMode w, h, 8, 0, updateRegistry : if stat = 0 : return 0
      TryChangeDisplayMode w, h, 0, 0, updateRegistry : if stat = 0 : return 1
      return 2
    case 2:
      TryChangeDisplayMode w, h, 32, 0, updateRegistry : if stat = 0 : return 0
      TryChangeDisplayMode w, h, 24, 0, updateRegistry : if stat = 0 : return 0
      TryChangeDisplayMode w, h, 16, 0, updateRegistry : if stat = 0 : return 0
      TryChangeDisplayMode w, h, 0, 0, updateRegistry : if stat = 0 : return 1
      return 2
  swend
  return 2
#global

chgdisp2 2, 1024, 768, 1
end