Open棟梁Project - マイクロソフト系技術情報 Wiki

* 目次 [#k61a7539]
#contents

*概要 [#cd7740e7]
「Windowを前面に出す」方法については、~
過去に似た問い合わせを何回も受けているため纏めておきます。

技術的背景については、「[[ウィンドウ・システム]]」を参照のこと。

*SetForegroundWindow [#v4c4f7e8]
ウィンドウの制御をプログラムから行う場合は、~
SetForegroundWindowのWin32 APIを使用できますが、~

**使用条件 [#f36f2d65]
SetForegroundWindowを使用する場合、以下の様な条件があるようです。

-[WinSDK] ウィンドウを前面に出す方法ヘニックスのライブ小屋~
http://phoenix3430025.wordpress.com/2012/01/04/winsdk-%E3%82%A6%E3%82%A3%E3%83%B3%E3%83%89%E3%82%A6%E3%82%92%E5%89%8D%E9%9D%A2%E3%81%AB%E5%87%BA%E3%81%99%E6%96%B9%E6%B3%95/

--SetForegroundWindow 関数~
http://msdn.microsoft.com/ja-jp/library/cc411039.aspx

>MSDNによると、

+++そのプロセスがフォアグラウンドプロセスである。 
+++そのプロセスはフォアグラウンドプロセスにより開始された。 
+++そのプロセスが最後の入力イベントを受け取った。 
+++フォアグラウンドプロセスがない。 
+++フォアグラウンドプロセスがデバッグ中である。 
+++フォアグラウンドがロックされていない~
(LockSetForegroundWindow 関数の説明を参照)。 
+++フォアグラウンドロックのタイムアウトが発生している~
( 関数の SPI_GETFOREGROUNDLOCKTIMEOUT の説明を参照)。 

-SetForegroundWindow でアクティブにならない場合には?~
http://hpcgi1.nifty.com/MADIA/VBBBS2/wwwlng.cgi?print+200402/04020031.txt

**AttachThreadInput [#v22896f3]

【C#】アクティブでないアプリケーションのFormを~
-【C#】アクティブでないアプリケーションのFormを~
アクティブ表示に変更したい - Insider.NET - @IT~
http://www.atmarkit.co.jp/bbs/phpBB/viewtopic.php?topic=32993&forum=7

基本的にアクティブにした際(切り替え時)は、タスクバーが点滅するだけですが、~
>基本的にアクティブにした際(切り替え時)は、タスクバーが点滅するだけですが、~
このウインドウを、最前面に出すのは、以下のような処理が必要になります。

-VB初心者友の会 - Q&A掲示板過去ログ~
2302-2アプリケーションの切替方法について井藤君@ビギナー~
http://www.gizcollabo.jp/vbtomo/log/archive/vbqanda_2302_2.html

>#2360-3~
RE#2347:アプリケーションの切替方法について~
>#2360-3 RE#2347:アプリケーションの切替方法について~
■ゆー太郎2001-12-03(月) 23:43~
 > SetForegroundWindow を使うのが今までの手法だったのですが、Win98 から OS の
 > 動作が変わりました。タスクバー上で点滅するのみになります。
 > 
 > これは「プログラムが勝手に、前面のウインドウを操作するのはおかしい。」という
 > 考えを元にしてます。なので、ご希望の動作は、「出来ない/してはならない」こと
 > になります。(-_-;)
 > 
 
 それでも無理やり やりたいのであれば、
 AttachThreadInput API関数で無理やり現在アクティなブスレッドに
 自分のスレッドをアタッチして、その間にBringWindowToTop API関数で
 自分のフォームを前面に出します。
 その後もう一度AttachThreadInput API関数でデタッチして解除すれば可能です。
 もちろん、Windowsの仕様に反しますが。

>SetForegroundWindow を使うのが今までの手法だったのですが、~
Win98 からOS の動作が変わりました。~
タスクバー上で点滅するのみになります。

>これは~
 「プログラムが勝手に、前面のウインドウを操作するのはおかしい。」~
という考えを元にしてます。~

>なので、ご希望の動作は、「出来ない/してはならない」ことになります。(-_-;)~

>それでも無理やり やりたいのであれば、~
AttachThreadInput Win32 APIで無理やり現在アクティブなスレッドに~
自分のスレッドをアタッチして、その間にBringWindowToTop API関数で~
自分のフォームを前面に出します。

>その後もう一度AttachThreadInput API関数でデタッチして解除すれば可能です。~

***補足説明(VIQとローカル入出力の統合) [#xc66e4c8]
この処理を「VIQとローカル入出力の統合」と言う。

AttachThreadInput Win32 APIで、VIQを共有すれば、当該プロセスが、~
>「そのプロセスが最後の入力イベントを受け取った。」

ということになり、タスクバーを点滅させずに、ウインドウを最前面に出すことができる。

ただし、Windows標準の操作性では無いため、~
こちらも基本的にはあまり実装しない方が良い。

*Vista以降(SetWindowPos) [#v015e4d3]
Vista以降ではSetWindowPosのWin32 APIを使用できます。

-winapi - How can I bring a window to the foreground in Vista using C++ - Stack Overflow~
http://stackoverflow.com/questions/534241/how-can-i-bring-a-window-to-the-foreground-in-vista-using-c

-ウィンドウのフォアグラウンド化 - cocoamixの日記~
http://d.hatena.ne.jp/cocoamix/20090528/1243475334

-Vista で Excel を最前面に表示~
http://moosoft.jp/index.php?option=com_content&view=article&id=76&Itemid=106

*Webからだと(ActiveX) [#cf2eb71f]
前述のWin32 APIを使用する必要があるため、IEの場合、~
ActiveXを使用する必要があります。javascriptでは実現不可能です。

*その他 [#e06169de]

**常に最前面 [#j29d2165]
-フォームを常に最前面に表示させる~
(タスクマネージャー, SetWindowPos, user32.dll, TopMost) - いろいろ備忘録日記~
http://d.hatena.ne.jp/gsf_zero1/20100330/p1

**起動時だけ最前面 [#q17b6f21]

-@IT:.NET TIPS 多重起動禁止時に実行中の~
Windowsアプリケーションを最前面に表示するには? - C# VB.NET Windowsフォーム~
http://www.atmarkit.co.jp/fdotnet/dotnettips/151winshow/winshow.html

>ただし、起動プロセスのウィンドウを使用して最前面化する必要があります。

**Windowsの標準仕様 [#j6f2208d]
マイクロソフトの出しているユーザーエクスペリエンスガイドライン

-Windows User Experience Interaction Guidelines~
http://msdn.microsoft.com/en-us/library/aa511258.aspx

に、Z order に関する記述があります(P479)。~

これによると、他のプロセスのウィンドウを変更するなとあります。~
Windows 上のアプリケーションは、このガイドラインに従うべきであり、~
Z order は触らない方がいいということになります。


トップ   新規 一覧 単語検索 最終更新   ヘルプ   最終更新のRSS