VB2010からAccess起動の問題

解決


てぃん  2013-05-20 11:58:11  No: 148141  IP: [192.*.*.*]

以前質問させていただいた方法でVB2010からAccess2003を起動しています。
前回記事
http://madia.world.coocan.jp/cgi-bin/vbnet/wwwlng.cgi?print+201207/12070004.txt

この処理でフォームから印刷ボタンを押すとAccessが起動し、印刷プレビューが
表示されます。

複数のパソコンで試したところ、同じ条件(Windows7,Access2003)なのに
あるパソコンではAccessは起動するのですが、フォームの背面になり、Accessが前面に表示されません。

構文的に問題があるのか、別の原因なのかもわかりません。
詳しい方おられましたらアドバイスお願いします。

編集 削除
魔界の仮面弁士  2013-05-21 08:58:32  No: 148142  IP: [192.*.*.*]

昨夏に、同様の件で Microsoft の有償サポートに問い合わせたことがあります。
(自分の場合は、CreateObject からの Excel 起動でしたが)

アプリが背面起動する場合、下記が原因の可能性があるとのことです。
http://support.microsoft.com/kb/886217/ja

記載の通り、以下のレジストリを設定してみてください。
当方はそれで回避できています。
(設定後端末を再起動してください)

キー : HKEY_CURRENT_USER\Control Panel\Desktop
名前 : ForegroundLockTimeout (REG_DWORD)
値 : 0


事前設定が難しい場合や、他アプリへの影響範囲を抑えたい場合には、
  SPI_SETFOREGROUNDLOCKTIMEOUT
によって、一時的に設定を変更する手法があります。
この方法で回避できることも確認済みです。

(1) GetForegroundWindow + GetWindowThreadProcessId で
  現在のフォアグラウンドウィンドウのスレッドを取得

(2) 手順 1 で得たスレッドが自スレッドではなかった場合、
  AttachThreadInput で上記スレッドにアタッチする

(3) SPI_{GET|SET}FOREGROUNDLOCKTIMEOUT を
    SystemParametersInfo API に渡して、
    タイムアウトを 0 に一時的に変更する

(4) LockSetForegroundWindow で LSFW_UNLOCK を指定。

(5) 本題の SetForegroundWindow を呼び出して切り替える。
  http://msdn.microsoft.com/ja-jp/library/cc411039.aspx
  その後、下記の手順で後始末を行う

(6) SPI_SETFOREGROUNDLOCKTIMEOUT を再度呼び出して
  手順3 で 0 にしておいた設定を元の状態に復元する

(7) 手順2 でアタッチしていた場合は、それを
  AttachThreadInput でデタッチする


なお、Visual Studio 2010/2012 からテストする場合、
開発環境の起動時に、SPI_{GET/SET}FOREGROUNDLOCKTIMEOUT の値が
破壊される不具合が発見されています。(値とポインタを取り間違えたとのこと)
http://support.microsoft.com/kb/2763075/ja

この問題は実行環境には影響を与えませんが、開発環境でテストする場合には、
上記問題の回避のため、アプリ作成後は OS を再起動した上で、
Visual Studio を起動せずに EXE からの単体実行でテストしてください。
(あるいは、VS2008 以下のバージョンで検証するようにする)

編集 削除
てぃん  2013-05-22 20:46:18  No: 148143  IP: [192.*.*.*]

ありがとうございます。
無事解決しました。

Visual Studio 2010/2012 からテストする場合は注意しないといけませんね。

編集 削除