2017-04-19 9 views
0

アプリケーションA(例:AutoCAD、Wordなど)実行時に実行時にDLL Xを呼び出してタスクを実行する→フォームを開くログイン他のアプリケーションで1つのアプリケーションのフォームを閉じるにはどうすればいいですか?

アプリケーションB(例:Photoshop、Excelなど) 。)実行時には、タスクを実行するために実行時にDLL Yを呼び出す→私は上記のログインフォームを閉じることができますか?

これは可能ですか?

Image description

+1

cad、excelなどは本当に悪い例です。 –

+0

@LeiYang彼らはどんなものと同じくらい良いです、これはちょうどあなたがROTを台無しにしなければならないように開始するための良いアイデアではありません。 Oosutsukeあなたはgoogle ROTとタイマーで何かを実装するべきです – EpicKip

+0

@LeiYang:私はちょうど想像しやすいように**例(cad、word、...)が必要です。私はどのようにわからないので、私は誰かにアイデアを提案したい。 EpicKip:ありがとう。私はGoogle ROTになるよ! – Oosutsuke

答えて

0

次は、別のプロセスでウィンドウを閉じる方法を示す少しのサンプルです。新しいWindowsフォームプロジェクトを作成し、そこに2つのフォームを追加し、最初の1にある2つのボタンを追加し、Form1にそのコードを配置:

public partial class Form1 : Form 
{ 
    delegate bool EnumWindowsProc(IntPtr Hwnd, IntPtr lParam); 

    [DllImport("user32", SetLastError = true)] 
    [return: MarshalAs(UnmanagedType.Bool)] 
    private extern static bool EnumThreadWindows(int threadId, EnumWindowsProc callback, IntPtr lParam); 

    [DllImport("user32", SetLastError = true)] 
    [return: MarshalAs(UnmanagedType.Bool)] 
    static extern bool EnumChildWindows(IntPtr hwndParent, EnumWindowsProc lpEnumFunc, IntPtr lParam); 

    [DllImport("user32", SetLastError = true, CharSet = CharSet.Auto)] 
    private extern static int GetWindowText(IntPtr hWnd, StringBuilder text, int maxCount); 

    [DllImport("user32.dll", CharSet = CharSet.Auto)] 
    static extern IntPtr SendMessage(IntPtr hWnd, UInt32 Msg, IntPtr wParam, IntPtr lParam); 

    private const int WM_CLOSE = 0x10; 

    public Form1() 
    { 
     InitializeComponent(); 
     button1.Click += button1_Click; 
     button2.Click += button2_Click; 
    } 

    private void button1_Click(object sender, EventArgs e) 
    { 
     var frm = new Form2(); 
     frm.Show(this); 
    } 

    private void button2_Click(object sender, EventArgs e) 
    { 
     Process[] processes = Process.GetProcessesByName("FindWindowSample"); 

     foreach (Process p in processes) 
     { 
      var handle = FindWindowInProcess(p, x => x == "Form2"); 

      if (handle != IntPtr.Zero) 
      { 
       SendMessage(handle, WM_CLOSE, IntPtr.Zero, IntPtr.Zero); 
      } 
     } 
    } 

    public static IntPtr FindWindowInProcess(Process process, Func<string, bool> compareTitle) 
    { 
     IntPtr windowHandle = IntPtr.Zero; 

     foreach (ProcessThread t in process.Threads) 
     { 
      windowHandle = FindWindowInThread(t.Id, compareTitle); 
      if (windowHandle != IntPtr.Zero) 
      { 
       break; 
      } 
     } 

     return windowHandle; 
    } 

    private static IntPtr FindWindowInThread(int threadId, Func<string, bool> compareTitle) 
    { 
     IntPtr windowHandle = IntPtr.Zero; 
     EnumThreadWindows(threadId, (hWnd, lParam) => 
     { 
      StringBuilder text = new StringBuilder(200); 
      GetWindowText(hWnd, text, 200); 
      if (compareTitle(text.ToString())) 
      { 
       windowHandle = hWnd; 
       return false; 
      } 
      return true; 
     }, IntPtr.Zero); 

     return windowHandle; 
    } 
} 

コンパイルして、アプリケーションの2つのインスタンスを実行します。最初のボタン1をクリックしてForm2を表示します。 2番目のインスタンスでButton2をクリックして、最初のインスタンスからForm2を閉じます。

+1

これはすばらしいことです。それはOKを実行しました。あなたの努力のために非常にありがとう! +1 – Oosutsuke

+0

コードはどこですか:open word/cad ...とログインフォームを表示しますか? –

+0

@LeiYang:私はちょうど私の考えを簡単に想像するために読者に例を挙げたいと思う。 – Oosutsuke

0

もあればその実行を終了すると、最も簡単な方法は、おそらくあなたを開くため

using System.Diagnostics; 
var autocad = Process.GetProcesses().FirstOrDefault(w=>w.ProcessName == "AutoCAD"); 
autocad.Close(); 

のようなもののようになるproccessちょうど約可能性はおそらくサイクル必要と名のproccesses。それほど効率的ではありませんが、それだけであなたの仕事が終わってしまうでしょう。

+0

私は欲しいですAutoCADで開かれているフォームを閉じますが、AutoCADは終了しません(終了しません) – Oosutsuke

+0

したがって、autocadによって開かれるフォームを閉じようとしていますが、autocadのプロセス全体ではないダイアログだけを閉じようとしていますか? – subkonstrukt

+0

はい、それは本当です。 – Oosutsuke

0

ウィンドウレスのコンソールアプリケーションで新しいプロセスをチェックし続けることができます。

enter image description here
プレス:

  1. は、コンソールアプリケーションと

  2. コンソールアプリケーション、このようなWindowsアプリケーション作成し、ログインフォームを使用して新しいプロジェクトを作成します。私は例を持っていますプロパティ enter image description here Windowsアプリケーションの選択

    は、プロセスをチェックするコンソールアプリケーションでタイマーください:

    public static bool IsOpen = false; 
    
    static void Main(string[] args) 
    { 
        Timer t = new Timer(TimerCallback, null, 0, 1200); 
        while (true) 
        { 
         //keep it running 
        } 
    } 
    
    private static void TimerCallback(Object o) 
    { 
        if (!IsOpen && Process.GetProcesses().Select(r => r.ProcessName).Contains("EXCEL")) 
        { 
         //Excel is running, show the form 
         Form1 loginForm = new Form1(); 
         loginForm.ShowDialog(); 
         //Stop it from spawning a million forms by setting bool 
         IsOpen = true; 
        } 
    } 
    

    ロジックアプリケーションが閉じがあまりにもこのタイマーの内側に置くことができますフォームを閉じるために、それを同じように使用します。コンソールウィンドウからフォームを開くには

    しかし、あなたは、コンソールアプリケーションへの参照を追加する必要があります。
    だけでフォームを使用して、これを追加します。あなたは、プロセス名が必要な場合

    enter image description here

    foreach (var proc in Process.GetProcesses()) 
    { 
        MessageBox.Show(proc.ProcessName); 
    } 
    

    これは、現在実行中のすべてのプロセスの名前を表示します。

+0

ログインフォームは別のプロセスにありますか? –

+0

@LeiYangそれ自体が優れているわけではありません。 – EpicKip

+0

@LeiYangなぜあなたはこれをしたいと思うのか分かりませんが、このようにすることができます – EpicKip

関連する問題