フォームが画面の最後に配置された場所に関するユーザーの設定を記憶するアプリケーションを開発しています。場合によっては、ユーザーはそれを2番目の画面に表示し、後で2番目の画面なしでアプリを起動します(フォームが画面外に表示されることもあります)。また、ユーザーが解像度を変更すると、同様の効果が得られる場合もあります。
Form_Shownイベントハンドラーでこのチェックを実行したいと思っていました。基本的に、フォームが完全に画面から外れているかどうかを確認して、再配置できるようにします。
何かアドバイス?
フォームが完全に画面に表示されている:であるかどうかをこの関数で確認します。
public bool IsOnScreen( Form form )
{
Screen[] screens = Screen.AllScreens;
foreach( Screen screen in screens )
{
Rectangle formRectangle = new Rectangle( form.Left, form.Top,
form.Width, form.Height );
if( screen.WorkingArea.Contains( formRectangle ) )
{
return true;
}
}
return false;
}
チェック左上のポイントのみ画面に表示されているかどうか:
public bool IsOnScreen( Form form )
{
Screen[] screens = Screen.AllScreens;
foreach( Screen screen in screens )
{
Point formTopLeft = new Point( form.Left, form.Top );
if( screen.WorkingArea.Contains( formTopLeft ) )
{
return true;
}
}
return false;
}
上記のすべてのソリューションを「IntersectsWith」メソッドおよびLINQ拡張機能と組み合わせると、簡単に言えば次のようになります。
public bool IsOnScreen(Form form)
{
// Create rectangle
Rectangle formRectangle = new Rectangle(form.Left, form.Top, form.Width, form.Height);
// Test
return Screen.AllScreens.Any(s => s.WorkingArea.IntersectsWith(formRectangle));
}
ここで完全な解決策(すべての回答に基づく)。パラメータMinPercentOnScreen
を追加しました。この場合、少なくともこの%のピクセルがすべての画面/ディスプレイで表示される必要があります。したがって、これがfalse
を返す場合は、ウィンドウの位置をデフォルトに戻す必要があります。
// Return True if a certain percent of a rectangle is shown across the total screen area of all monitors, otherwise return False.
public bool IsOnScreen(System.Drawing.Point RecLocation, System.Drawing.Size RecSize, double MinPercentOnScreen = 0.2)
{
double PixelsVisible = 0;
System.Drawing.Rectangle Rec = new System.Drawing.Rectangle(RecLocation, RecSize);
foreach (Screen Scrn in Screen.AllScreens)
{
System.Drawing.Rectangle r = System.Drawing.Rectangle.Intersect(Rec, Scrn.WorkingArea);
// intersect rectangle with screen
if (r.Width != 0 & r.Height != 0)
{
PixelsVisible += (r.Width * r.Height);
// tally visible pixels
}
}
return PixelsVisible >= (Rec.Width * Rec.Height) * MinPercentOnScreen;
}
実装:
return IsOnScreen(this.Location, this.Size);
古いスレッドですが、それでも役に立ちます! CodyとAndrija-コードをありがとう。 screen.WorkingArea.Intersect(formRectangle);の代わりに、いくつかの小さな調整を行う必要がありました。 formRectangle.Intersect(screen.WorkingArea);を使用しました。 Intersect()は、そのオブジェクトを交差に置き換えるためです。フォームが完全に画面から外れている場合、交差後のformRectangleは(0,0,0,0)であり、Contains()はtrueを返します。したがって、trueを返す前に、formRectangleのTop、Left、Width、Heightがすべて0ではないかどうかも確認します。これで、フォームのいずれかの部分が画面に表示されている場合、コードはtrueを返し、画面に表示されている部分がない場合はfalseを返します。
モニターがオフになっている場合、これらはいずれも機能しません。 Screen.AllScreens関数は、画面がオフの場合でも常に画面数を返します。
[〜#〜] wpf [〜#〜]の場合(Matthias Loerkesの回答に基づく)
System.Windows.FormsおよびSystem.Drawingへの参照を追加します。
//using System.Windows.Forms;
public bool IsOnScreen(Window window)
{
var windowRect = new System.Drawing.Rectangle((int)window.Left, (int)window.Top, (int)window.Width, (int)window.Height);
return Screen.AllScreens.Any(s => s.WorkingArea.IntersectsWith(windowRect));
}
ウィンドウを配置する前に、画面の解像度を確認してください。これにより、実際に実行する前に、解像度の範囲外に配置するかどうかを判断できます。