目的
必要なこと
- 最前面指定
- フォーム非表示
- 画像表示
- 画面中央配置
以上の4つです。
最前面指定
フォーム非表示
private void Form1_Shown(object sender, EventArgs e)
{
Visible = false;
}
このイベントををformクラスに入れる
フォームを非表示で子要素を表示することはできそうにない・・・
フォームを透明化+上のバーをなくす
FormBorderSytleをNoneにすることで、上のバーを無くし
こんな感じにする
this.TransparencyKey = this.BackColor;
でフォームを透明化する。
画像表示
PictureBoxを使用
ディスプレイのサイズを取得
画像がディスプレイの中心に来るようフォームの位置を調整する。
完了
完成プログラム参照
非アクティブ時にキー入力で終了させる
WindowsAPIの機能を使う
完成したプログラム
フォルダ内に表示する画像を入れてください。
画像の名前に合わせてプログラムを修正してください。
デフォルトでpキーでソフト終了にしてます。
using System.Diagnostics;
using System.Runtime.InteropServices;
namespace DotSight
{
public partial class Form1 : Form
{
//キーボードフッククラスのインスタンス生成
KeyboardHook _hook = new KeyboardHook();
public Form1()
{
InitializeComponent();
}
private void Form1_Load(object sender, EventArgs e)
{
//ディスプレイの高さ
int h = System.Windows.Forms.Screen.PrimaryScreen.Bounds.Height;
//ディスプレイの幅
int w = System.Windows.Forms.Screen.PrimaryScreen.Bounds.Width;
//結果表示
//label1.Text = "ディスプレイの高さ:"+ h.ToString() +"ピクセル";
//label2.Text = "ディスプレイの幅:" + w.ToString() + "ピクセル";
Image image = Image.FromFile(@"C:/Users/yellow_site.png");
pictureBox1.Image = image;
//画像のサイズを取得する
int h_png = image.Height;
int w_png = image.Width;
//フォームの場所を調整する
this.Location = new Point((int)((w-w_png)/2),(int)((h-h_png)/2));
//キーボードが押された時のイベントハンドラを登録
_hook.OnKeyDown += ( s , ea) =>
{
//イベント発生時の処理
//Console.WriteLine(ea.Key);
ea.RetCode = 0; //他のプログラムにキーを転送したくない場合は1を代入,それ以外は0
if (ea.Key.ToString() == "P")
{
//アプリ終了
_hook.UnHook();
this.Close();
}
};
//キーボードフックの開始
_hook.Hook();
}
private void label1_Click(object sender, EventArgs e)
{
}
private void Form1_Shown(object sender, EventArgs e)
{
//this.Visible = false;
//pictureBox1.Visible = true;
this.TransparencyKey = this.BackColor;
}
private void pictureBox1_Click(object sender, EventArgs e)
{
}
}
public class KeyboardHook
{
private const int WH_KEYBOARD_LL = 0x0D;
private const int WM_KEYBOARD_DOWN = 0x100;
private const int WM_KEYBOARD_UP = 0x101;
private const int WM_SYSKEY_DOWN = 0x104;
private const int WM_SYSKEY_UP = 0x105;
//イベントハンドラの定義
public event EventHandler<KeyboardHookEventArgs> OnKeyDown = delegate { };
public event EventHandler<KeyboardHookEventArgs> OnKeyUp = delegate { };
//コールバック関数のdelegate 定義
private delegate IntPtr HookCallback(int nCode, IntPtr wParam, IntPtr lParam);
//キーボードフックに必要なDLLのインポート
[DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = true)]
private static extern IntPtr CallNextHookEx(IntPtr hhk, int nCode, IntPtr wParam, IntPtr lParam);
[DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = true)]
private static extern IntPtr SetWindowsHookEx(int idHook, HookCallback lpfn, IntPtr hMod, uint dwThreadId);
[DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = true)]
[return: MarshalAs(UnmanagedType.Bool)]
private static extern bool UnhookWindowsHookEx(IntPtr hhk);
[DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
private static extern IntPtr GetModuleHandle(string lpModuleName);
//フックプロシージャのハンドル
private static IntPtr _hookHandle = IntPtr.Zero;
//フック時のコールバック関数
private static HookCallback _callback;
/// <summary>
/// キーボードHook の開始
/// </summary>
/// <param name="callback"></param>
public void Hook()
{
_callback = CallbackProc;
using (Process process = Process.GetCurrentProcess())
{
using (ProcessModule module = process.MainModule)
{
_hookHandle = SetWindowsHookEx(
WH_KEYBOARD_LL, //フックするイベントの種類
_callback, //フック時のコールバック関数
GetModuleHandle(module.ModuleName), //インスタンスハンドル
0 //スレッドID(0:全てのスレッドでフック)
);
}
}
}
/// <summary>
/// コールバック関数
/// </summary>
/// <param name="nCode"></param>
/// <param name="wParam"></param>
/// <param name="lParam"></param>
/// <returns></returns>
private IntPtr CallbackProc(int nCode, IntPtr wParam, IntPtr lParam)
{
var args = new KeyboardHookEventArgs();
Keys key = (Keys)(short)Marshal.ReadInt32(lParam);
args.Key = key;
if ((int)wParam == WM_KEYBOARD_DOWN || (int)wParam == WM_SYSKEY_DOWN) OnKeyDown(this, args);
if ((int)wParam == WM_KEYBOARD_UP || (int)wParam == WM_SYSKEY_UP) OnKeyUp(this, args);
return (args.RetCode == 0) ? CallNextHookEx(_hookHandle, nCode, wParam, lParam) : (IntPtr)1;
}
/// <summary>
/// キーボードHockの終了
/// </summary>
public void UnHook()
{
UnhookWindowsHookEx(_hookHandle);
_hookHandle = IntPtr.Zero;
}
}
/// <summary>
/// キーボードフックのイベント引数
/// </summary>
public class KeyboardHookEventArgs
{
public Keys Key { get; set; }
public int RetCode { get; set; } = 0;
}
}
フォームデザイン
namespace DotSight
{
partial class Form1
{
/// <summary>
/// Required designer variable.
/// </summary>
private System.ComponentModel.IContainer components = null;
/// <summary>
/// Clean up any resources being used.
/// </summary>
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
protected override void Dispose(bool disposing)
{
if (disposing && (components != null))
{
components.Dispose();
}
base.Dispose(disposing);
}
#region Windows Form Designer generated code
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
private void InitializeComponent()
{
this.pictureBox1 = new System.Windows.Forms.PictureBox();
((System.ComponentModel.ISupportInitialize)(this.pictureBox1)).BeginInit();
this.SuspendLayout();
//
// pictureBox1
//
this.pictureBox1.Location = new System.Drawing.Point(0, 0);
this.pictureBox1.Name = "pictureBox1";
this.pictureBox1.Size = new System.Drawing.Size(130, 113);
this.pictureBox1.TabIndex = 2;
this.pictureBox1.TabStop = false;
this.pictureBox1.Click += new System.EventHandler(this.pictureBox1_Click);
//
// Form1
//
this.AutoScaleDimensions = new System.Drawing.SizeF(7F, 15F);
this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
this.ClientSize = new System.Drawing.Size(214, 250);
this.Controls.Add(this.pictureBox1);
this.FormBorderStyle = System.Windows.Forms.FormBorderStyle.None;
this.Name = "Form1";
this.Text = "Form1";
this.TopMost = true;
this.Load += new System.EventHandler(this.Form1_Load);
this.Shown += new System.EventHandler(this.Form1_Shown);
((System.ComponentModel.ISupportInitialize)(this.pictureBox1)).EndInit();
this.ResumeLayout(false);
}
#endregion
private PictureBox pictureBox1;
}
}
追記
キー入力イベントクラス
作成者様ありがとうございます。
すぐ使えるように、自分用にメモを残します。
form_load内部
//キーボードが押された時のイベントハンドラを登録
_hook.OnKeyDown += (s, ea) =>
{
//イベント発生時の処理
//Console.WriteLine(ea.Key);
ea.RetCode = 0; //他のプログラムにキーを転送したくない場合は1を代入,それ以外は0
textBox1.Text = ea.Key.ToString();
if (ea.Key.ToString() == "P")
{
//アプリ終了
_hook.UnHook();
this.Close();
}
if (ea.Key.ToString() == "Right")
{
screen_shot();
}
};
//キーボードフックの開始
_hook.Hook();
クラス、namespaceに追加
public class KeyboardHook
{
private const int WH_KEYBOARD_LL = 0x0D;
private const int WM_KEYBOARD_DOWN = 0x100;
private const int WM_KEYBOARD_UP = 0x101;
private const int WM_SYSKEY_DOWN = 0x104;
private const int WM_SYSKEY_UP = 0x105;
//イベントハンドラの定義
public event EventHandler<KeyboardHookEventArgs> OnKeyDown = delegate { };
public event EventHandler<KeyboardHookEventArgs> OnKeyUp = delegate { };
//コールバック関数のdelegate 定義
private delegate IntPtr HookCallback(int nCode, IntPtr wParam, IntPtr lParam);
//キーボードフックに必要なDLLのインポート
[DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = true)]
private static extern IntPtr CallNextHookEx(IntPtr hhk, int nCode, IntPtr wParam, IntPtr lParam);
[DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = true)]
private static extern IntPtr SetWindowsHookEx(int idHook, HookCallback lpfn, IntPtr hMod, uint dwThreadId);
[DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = true)]
[return: MarshalAs(UnmanagedType.Bool)]
private static extern bool UnhookWindowsHookEx(IntPtr hhk);
[DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
private static extern IntPtr GetModuleHandle(string lpModuleName);
//フックプロシージャのハンドル
private static IntPtr _hookHandle = IntPtr.Zero;
//フック時のコールバック関数
private static HookCallback _callback;
/// <summary>
/// キーボードHook の開始
/// </summary>
/// <param name="callback"></param>
public void Hook()
{
_callback = CallbackProc;
using (Process process = Process.GetCurrentProcess())
{
using (ProcessModule module = process.MainModule)
{
_hookHandle = SetWindowsHookEx(
WH_KEYBOARD_LL, //フックするイベントの種類
_callback, //フック時のコールバック関数
GetModuleHandle(module.ModuleName), //インスタンスハンドル
0 //スレッドID(0:全てのスレッドでフック)
);
}
}
}
/// <summary>
/// コールバック関数
/// </summary>
/// <param name="nCode"></param>
/// <param name="wParam"></param>
/// <param name="lParam"></param>
/// <returns></returns>
private IntPtr CallbackProc(int nCode, IntPtr wParam, IntPtr lParam)
{
var args = new KeyboardHookEventArgs();
Keys key = (Keys)(short)Marshal.ReadInt32(lParam);
args.Key = key;
if ((int)wParam == WM_KEYBOARD_DOWN || (int)wParam == WM_SYSKEY_DOWN) OnKeyDown(this, args);
if ((int)wParam == WM_KEYBOARD_UP || (int)wParam == WM_SYSKEY_UP) OnKeyUp(this, args);
return (args.RetCode == 0) ? CallNextHookEx(_hookHandle, nCode, wParam, lParam) : (IntPtr)1;
}
/// <summary>
/// キーボードHockの終了
/// </summary>
public void UnHook()
{
UnhookWindowsHookEx(_hookHandle);
_hookHandle = IntPtr.Zero;
}
}
/// <summary>
/// キーボードフックのイベント引数
/// </summary>
public class KeyboardHookEventArgs
{
public Keys Key { get; set; }
public int RetCode { get; set; } = 0;
}