分享

How to use Visual C++ to close another application

 xubin2016 2015-01-16
This article was previously published under Q307395

Collapse imageOn This Page

Collapse imageSUMMARY

This article describes how to close another application from within your application. This article also describes how to close a specific instance of another application, such as Notepad, if more than one instance of the application is running.

Declare Variables

You must define several variables. Because these variables are used in multiple methods, define them outside any procedure so that they remain in scope.

The first variable is an array to hold the process objects that the GetProcessByName method returns. In this code, "procName" is a String variable that is used to hold the name of the process:
private:
   Process *processes[];
   static String *procName = S"Notepad";

Obtain a List of Application Instances

The following code for the BuildList function is called each time a new instance of Notepad is created. This example stores the process information in a ListView control. The code to populate the ListView control is included only for consistency with the complete example that follows.

The most important part of this code is the call to the GetProcessByName method of the Process class. This method returns an array of Process object pointers, which can be iterated over by using a For loop.
ListViewItem *itemAdd ; 
ListView1->Items->Clear();
processes = Process::GetProcessesByName(procName);
for (int i = 0; i < processes->Length; i++)
{
   itemAdd = ListView1->Items->Add(processes[i]->MainWindowTitle);
   itemAdd->SubItems->Add(processes[i]->Id.ToString());
}

Close a Specific Instance of an Application

When you have multiple instances of an application running, if you want to close one instance, you must differentiate between those processes. This example uses the Id property to differentiate between the processes. The Id property and the MainWindowTitle property are stored in the ListView control.

This code gets the item that is currently selected in the ListView control, obtains a reference to the process by using the GetProcessById method of the Process class, and then closes that process by calling the CloseMainWindow method. Note that you cannot rebuild the list before the process has exited fully because the WaitForExit method of the Process class prevents this.
try
{         
   ListViewItem *lvi = ListView1->SelectedItems->get_Item(0);
   ListViewItem::ListViewSubItem *lvsi = lvi->SubItems->get_Item(1);
   int procID = System::Convert::ToInt32(lvsi->Text);
   Process *tempProc=Process::GetProcessById(procID);
   tempProc->CloseMainWindow();
   tempProc->WaitForExit();
   BuildList();
}
catch(...)
{
   MessageBox::Show(S"Select a process in the ListView.");
}
				

Close All Instances of an Application

To close all instances of a particular application, walk the array that the GetProcessByName method returns, and then call the CloseMainWindow method on each process object.
try
{
   for (int i = 0; i < processes->Length; i++)
   {
      processes[i]->CloseMainWindow();
   }

   ListView1->Items->Clear();
}
catch (System::NullReferenceException *)
{
   MessageBox::Show("No instances of Notepad running.");
}
				

Step-by-Step Example

  1. Create a new Managed C++ Application in Microsoft Visual Studio .NET or Microsoft Visual Studio 2005. To do this, follow these steps:
    1. Start Visual Studio .NET or Visual Studio 2005.
    2. On the File menu, point to New, and then click Project.
    3. In the New Project dialog box, click Visual C++ Projects under Project Types, and then click Managed C++ Application for Visual Studio .NET 2002, click Console Application (.NET) for Visual Studio .NET 2003, or click CLR Console Application for Visual Studio 2005 under Templates.
    4. Type a file name in the Name box.
  2. In Solution Explorer, open the project .cpp file.
  3. Replace the code in the Code window with the following:
    #include "stdafx.h"
    #include <windows.h>
    #ifdef MessageBox
    #undef MessageBox
    #endif
    
    #using <mscorlib.dll>
    #using "System.Dll"
    #using "System.Windows.Forms.Dll"
    #using "System.Drawing.Dll"
    
    using namespace System;
    using namespace System::Drawing;
    using namespace System::Collections;
    using namespace System::ComponentModel;
    using namespace System::Windows::Forms;
    using namespace System::Diagnostics;
    
    namespace CloseApplication_mc
    {
       public __gc class Form1 : public Form
       {
       protected:
          Button *btnCloseAll;
          ColumnHeader *ColumnHeader2;
          ColumnHeader *ColumnHeader1;
          Button *btnLaunch1;
          ListView *ListView1;
          Button *btnClose1;
    
       private:
          Process *processes[];
          static String *procName = S"Notepad";
          static String *specialFolder = Environment::GetFolderPath(Environment::SpecialFolder::System);
    
       public:
          Form1()
          {
             InitForm();
          }
    
       protected:
          void Dispose( bool disposing )
          {
             Form::Dispose(disposing);
          }
    
       private:
          void InitForm()
          {
             btnClose1 = new Button();
             ColumnHeader2 = new ColumnHeader();
             ColumnHeader1 = new ColumnHeader();
             btnCloseAll = new Button();
             btnLaunch1 = new Button();
             ListView1 = new ListView();
             SuspendLayout();
    
             // 
             // btnClose1
             // 
             btnClose1->Location = Point(160, 176);
             btnClose1->Name = S"btnClose1";
             btnClose1->Size = System::Drawing::Size(112, 32);
             btnClose1->TabIndex = 4;
             btnClose1->Text = S"Close Selected Process";
             btnClose1->Click += new System::EventHandler(this, btnClose1_Click);
             Controls->Add(btnClose1);
    
             // 
             // btnCloseAll
             // 
             btnCloseAll->Location = Point(160, 216);
             btnCloseAll->Name = S"btnCloseAll";
             btnCloseAll->Size = System::Drawing::Size(112, 32);
             btnCloseAll->TabIndex = 3;
             btnCloseAll->Text = S"Close All Processes";
             btnCloseAll->Click += new System::EventHandler(this, btnCloseAll_Click);
             Controls->Add(btnCloseAll);
    
             // 
             // btnLaunch1
             // 
             btnLaunch1->Location = Point(32, 176);
             btnLaunch1->Name = S"btnLaunch1";
             btnLaunch1->Size = System::Drawing::Size(112, 72);
             btnLaunch1->TabIndex = 1;
             btnLaunch1->Text = S"Start Notepad";
             btnLaunch1->Click += new System::EventHandler(this, btnLaunch1_Click);
             Controls->Add(btnLaunch1);
    
             // 
             // ColumnHeader2
             // 
             ColumnHeader2->Text = S"Process ID";
             ColumnHeader2->Width = 85;
    
             // 
             // ColumnHeader1
             // 
             ColumnHeader1->Text = S"Window Title";
             ColumnHeader1->Width = 160;
    
             // 
             // ListView1
             // 
             ListView1->Columns->Add(ColumnHeader1);
             ListView1->Columns->Add(ColumnHeader2);
             ListView1->Location = Point(22, 8);
             ListView1->MultiSelect = false;
             ListView1->Name = S"ListView1";
             ListView1->Size = System::Drawing::Size(250, 152);
             ListView1->TabIndex = 7;
             ListView1->View = View::Details;
             Controls->Add(ListView1);
    
             // 
             // Form1
             // 
             AutoScaleBaseSize = System::Drawing::Size(5, 13);
             ClientSize = System::Drawing::Size(292, 266);
             Name = S"Form1";
             Text = S"Process Example";
             Closing += new System::ComponentModel::CancelEventHandler(this, closing);
             Load += new System::EventHandler(this, Form1_Load);
             ResumeLayout(false);
          }
    
          void BuildList()
          {
             ListViewItem *itemAdd ; 
             ListView1->Items->Clear();
             processes = Process::GetProcessesByName(procName);
             for (int i = 0; i < processes->Length; i++)
             {
                itemAdd = ListView1->Items->Add(processes[i]->MainWindowTitle);
                itemAdd->SubItems->Add(processes[i]->Id.ToString());
             }
          }
    
          void btnLaunch1_Click(Object *sender, EventArgs *e)
          {
             ProcessStartInfo *p = new ProcessStartInfo();
             p->FileName = String::Concat(specialFolder, S"\\eula.txt");
             p->WindowStyle = ProcessWindowStyle::Minimized ;
             Process *proc = Process::Start(p);
             proc->WaitForInputIdle();
             BuildList();
          }
    
          void Form1_Load(Object *sender, EventArgs *e)
          {
          }
    
          void btnClose1_Click(Object *sender, EventArgs *e)
          {
             try
             {         
                ListViewItem *lvi = ListView1->SelectedItems->get_Item(0);
                ListViewItem::ListViewSubItem *lvsi = lvi->SubItems->get_Item(1);
                int procID = System::Convert::ToInt32(lvsi->Text);
                Process *tempProc=Process::GetProcessById(procID);
                tempProc->CloseMainWindow();
                tempProc->WaitForExit();
                BuildList();
             }
             catch(...)
             {
                MessageBox::Show(S"Select a process in the ListView before clicking this button.");
             }
          }
    
          void btnCloseAll_Click(Object *sender, EventArgs *e)
          {
             if (processes != 0)
             {
                for (int i = 0; i < processes->Length; i++)
                {
                   processes[i]->CloseMainWindow();
                }
           
                ListView1->Items->Clear();
             }
          }
    
          void closing(Object *sender, System::ComponentModel::CancelEventArgs *e)
          {
             btnCloseAll_Click(this,e);
          }
       };
    } 
    
    using namespace CloseApplication_mc;
    
    int APIENTRY WinMain(HINSTANCE hInstance,
                         HINSTANCE hPrevInstance,
                         LPTSTR    lpCmdLine,
                         int       nCmdShow)
    {
       Form1 *FormInstance = new Form1;
       Application::Run(FormInstance);
    
       return 0;
    }
    					
  4. Build and then run the application.
  5. Click Start Notepad one or more times.
  6. Click an instance of Notepad in the ListView box, and then click Close Process. This closes the specific instance of Notepad that you selected. You can also click Close All Processes to close all the instances of Notepad that are running.
Note This article uses the Id property of the Process class to differentiate between instances of the application. The Id property is good for this task because all process IDs are unique. You can use the WindowHandle property of a Process object to get the same results. Although you can use other properties, they are less suitable for this task. If you do not know the process ID, or if you have the handle of the main window, you can also use the MainWindowTitle property to help identify the correct instance. However, because the MainWindowTitle property may not be unique, you cannot guarantee that you are referring to the correct window. 

    本站是提供个人知识管理的网络存储空间,所有内容均由用户发布,不代表本站观点。请注意甄别内容中的联系方式、诱导购买等信息,谨防诈骗。如发现有害或侵权内容,请点击一键举报。
    转藏 分享 献花(0

    0条评论

    发表

    请遵守用户 评论公约

    类似文章 更多