2016-08-07 6 views
-1

私はC#アプリケーションでflashwindowex winapiを使用して、アイコントレイのIEウィンドウをフラッシュします。コードにブレークポイントを追加してデバッグで実行すると、コードはうまく動作しています。しかし、ブレークポイントが削除されても、同じコードは機能しません。ウィンドウを点滅する

これはコンソールアプリケーションです。私は作成されたIEプロセスのハンドルをその名前で見つけるためにいくつかのウィンドウAPIを使用しています。プロセスのハンドルは、さらにプロセスを点滅させるためにFlashWindowEX WINAPIに渡されます。

public static System.IntPtr hnd = IntPtr.Zero; 
public delegate bool CallBackPtr(IntPtr hwnd, int lParam); 
public static CallBackPtr callBackPtr; 
public const UInt32 FLASH_T = 3; 
public const UInt32 FLASH_S = 12; 

static void Main(string[] args) 
{ 
    try 
    { 
     OrigCode(); 
    } 
    catch (Exception ex) 
    { 
     Console.WriteLine(ex.Message); 
    } 
    Console.ReadLine(); 
} 

public static void OrigCode() 
{ 
    string strPzszPath = string.Empty; 
    string strCommandLine = string.Empty; 
    string strpath1 = "http://localhost/Till/Default.aspx"; 

    strPzszPath = string.Concat(strPzszPath, strpath1); 
    strPzszPath = string.Concat(strPzszPath, "?TSCashierID=JILL&TSBalPeriod=2&TSBalDate=2015-06-02"); 
    strCommandLine = strPzszPath; 
    Process procRequested = new Process(); 

    ////Create the process in minimised mode by default 
    procRequested.StartInfo.WindowStyle = ProcessWindowStyle.Minimized; 
    procRequested.StartInfo.UseShellExecute = false; 

    ////Get the file name in which process is required to be started 
    procRequested.StartInfo.FileName = @"C:\Program Files\Internet Explorer\IExplore.exe"; 

    procRequested.StartInfo.Arguments = strCommandLine; 

    ////Start the process, process should be created in minimised mode 
    procRequested.Start(); 

    callBackPtr = new CallBackPtr(SetFocusEnum); 
    int intResult = EnumWindows(callBackPtr, 0); 

    FLASHWINFO fi = new FLASHWINFO(); 
    fi.cbSize = Convert.ToUInt32(Marshal.SizeOf(fi)); 
    fi.hwnd = hnd; 
    fi.dwFlags = FLASH_T | FLASH_S; 
    fi.ucount = UInt32.MaxValue; 
    fi.dwTimeout = 0; 
    FlashWindowEx(ref fi); 
} 

private static bool SetFocusEnum(IntPtr hWnd, int intLParam) 
{ 
    int intSize = GetWindowTextLength(hWnd); 
    try 
    { 

     if (intLParam == 0) //Process created so check by name 
     { 
      if (intSize++ > 0) 
      { 

       //Capture the running window name 
       StringBuilder sbWindowName = new StringBuilder(intSize); 
       GetWindowText(hWnd, sbWindowName, intSize); 
       //Capture the running process with the window name 
       if (sbWindowName.ToString().Contains("My Web Application Title")) 
       { 
       //Capture the handle which will be used to set the focus 
       hnd = hWnd; 
       } 
      } 
     } 
    } 
    catch (Exception ex) 
    { 
    } 
    finally 
    { 
    } 
    return true; 
} 

以下は、私が使用WINAPI関数は、次のとおりです。

[DllImport("user32.dll", CharSet = CharSet.Unicode)] 
internal static extern int EnumWindows(CallBackPtr callPtr, int intProc); 

[DllImport("user32.dll", CharSet = CharSet.Unicode)] 
internal static extern int GetWindowTextLength(IntPtr intptrHwnd); 

[DllImport("user32.dll", CharSet = CharSet.Unicode)] 
internal static extern int GetWindowText(IntPtr intptrHwnd, StringBuilder strText, int intMaxCount); 

[DllImport("user32.dll")] 
[return: MarshalAs(UnmanagedType.Bool)] 
private static extern bool FlashWindowEx(ref FLASHWINFO pwfi); 

[StructLayout(LayoutKind.Sequential)] 
private struct FLASHWINFO 
{ 
    public UInt32 cbSize; 
    public IntPtr hwnd; 
    public UInt32 dwFlags; 
    public UInt32 ucount; 
    public UInt32 dwTimeout; 
} 
+0

我々が持っている上に行くには何も持っていない場合、我々はあなたを助けることができない、あなたのコードを表示してください。何が起こっているのか、何が起こっていないのかの説明は、コードなしではあまり役に立たない。 –

+0

こんにちは私は明日を共有することができます私の携帯電話とコードを介してクエリを投稿していますが、私はアプローチについて話している場合、私はこのリンクで示されているように同じ方法でflashwindoexを使用していますhttp://stackoverflow.com/questions/4889181/get-user-attention-ste-stealing-focus。私はenumwindows winapiとその値を使用しているそのウィンドウを処理する価値を得るために、私はflashwindowexメソッドに渡しています。 –

+0

私は現在自分の電話にもいるので、あなたの特定のコードなしでは大したことができません(私はあなたがすべてを正しく使用したことを確認することを望んでいました)。私はコンピュータにアクセスするときにテストを行います。 –

答えて

0

私は私のコメントで述べたように、ここでの問題は、それがウィンドウのテキストのためにより変更するページをロードするために時間がかかりすぎるということですEnumWindows()関数を実行する時刻。使用するコードはほぼ即時に実行されますが、プロセスを開いてページを読み込むには数百ミリ秒から数秒かかります。遅延を加えることは、問題を解決する最も簡単な回避策です。

は、ここに私がやったことだ:

procRequested.Start(); 
procRequested.WaitForInputIdle(); 

System.Threading.Thread.Sleep(750); //Wait for approximately 750 ms. 

それは通常Thread.Sleep()を使用して反対advicedされていますが、コンソールアプリケーションにいるので、それはそれは少し時間がユーザーの入力を遮断する以外あまり違いはありません。走る

Process.WaitForInputIdle()への呼び出しを追加したことに気づいたことがあります。これは、プロセスが起動プロセスを完了するまで待ちます(リソースの読み込みや、アプリケーションが実際に起動する前に)、実際にウィンドウが表示されることをいつ期待できるかを知ることができます。

場合によっては、750ミリ秒の遅延が十分でないと感じる場合は、1250などに上げてみてください。


EDIT:

フォーカスされたウィンドウが点滅しません(あなたが言うように)ので、以前のウィンドウに焦点を当て、右ウィンドウを再度集中することを使用するウィンドウハンドルを格納することができますFlashWindowExコードを実行させる前に。このため

次の2つのWinAPIの呼び出しが必要になります。

[DllImport("user32.dll")] 
private static extern IntPtr GetForegroundWindow(); 

[DllImport("user32.dll")] 
[return: MarshalAs(UnmanagedType.Bool)] 
static extern bool SetForegroundWindow(IntPtr hWnd); 
  • GetForegroundWindow()現在フォーカスウィンドウにウィンドウハンドルを取得します。

  • は、ウィンドウハンドルを指定して現在フォーカスしているウィンドウを設定します。

は、それからちょうどここで、これらの二つの機能を使用します。

IntPtr focusedhWnd = GetForegroundWindow(); //Get the window handle to the currently focused window. 

procRequested.Start(); 
procRequested.WaitForInputIdle(); 

System.Threading.Thread.Sleep(750); //Wait for approximately 750 ms. 

callBackPtr = new CallBackPtr(SetFocusEnum); 
int intResult = EnumWindows(callBackPtr, 0); 

SetForegroundWindow(focusedhWnd); //Focus the previously focused window again. 

FLASHWINFO fi = new FLASHWINFO(); 
fi.cbSize = Convert.ToUInt32(Marshal.SizeOf(fi)); 
fi.hwnd = hnd; 
fi.dwFlags = FLASH_T | FLASH_S; 
fi.ucount = UInt32.MaxValue; 
fi.dwTimeout = 0; 
FlashWindowEx(ref fi); 
+0

問題はあなたが言ったことと同じだったが、プロセスが時間を費やしているときはほとんどない。しかし、ブレークポイントの挿入中にコードの実行に関して先に言及したポイント。デバッグモードの間、フォーカスはVisual Studioにとどまるため、アプリケーションがフラッシュウィンドウexを呼び出すと、起動されたアプリケーションが点滅します。しかし、exeを通ってすぐに走っている間、フォーカスはトレイ内の最小化されたアプリケーションに行きますので、点滅しません。今度は新しい問題は、ウィンドウトレイに焦点を当てずにプロセスを作成して、このフラッシュウィンドウが表示されるようにすることです。 –

+0

@bhupeshjoshi:私はそれを助けることができます。私に数分を与える... –

+0

Thanx @visual Vincent私も同様にしています。 –

関連する問題