WM_CLOSEで閉じれないウィンドウを閉じるには?

このQ&Aのポイント
  • ウィンドウを強制終了する方法として、WM_CLOSEメッセージを使用することができます。
  • ただし、WM_CLOSEメッセージを送った場合、ウィンドウが閉じる前に「変更を保存しますか?」などのダイアログが表示されることがあります。
  • ダイアログを表示せずにウィンドウを強制終了するには、PostMessage関数を使用してWM_CLOSEメッセージを送信する方法があります。
回答を見る
  • ベストアンサー

WM_CLOSEで閉じれないウィンドウを閉じるには?

以下にソースを張ります。 #include <stdio.h> #include <windows.h> BOOL CALLBACK EnumWindowProc(HWND hwnd, LPARAM lp) { static bool is_first = true; DWORD style = ::GetWindowLong(hwnd, GWL_STYLE); DWORD dwPID; if ( ::IsWindow(hwnd) && ::IsWindowVisible(hwnd) && (style&WS_CAPTION) && !(style&WS_POPUP) ) { char buf[65536]; ::GetWindowText(hwnd, buf, 65535); GetWindowThreadProcessId( hwnd, &dwPID ); if ( buf[0] != '\0' ) { if ( is_first ) is_first = false; else //printf("%c\n", 1); printf("%s%d\n", buf,hwnd); } } return TRUE; } int main (void){ ::EnumWindows(EnumWindowProc, 0); HWND hWnd; printf("プロセスIDを入力:\n"); scanf("%d",&hWnd); if( hWnd != NULL ){ printf( "終了します。-- pause --\n" ); getchar(); PostMessage( hWnd, WM_CLOSE, 0, 0 ); }else{ printf( "起動してないウインドウズです。\n" ); } return 0; } これですとたとえばメモ帳を編集していたときに WM_CLOSE メッセージを送ったときに「変更を保存しますか?」のようなダイアログが出る アプリがあります。これをダイアログが出ずに強制終了するには どうしたらよいでしょか?よろしくお願いします。

質問者が選んだベストアンサー

  • ベストアンサー
回答No.1

WM_DESTROYをポストすると消えます(消えないのもあるが)。 当たり前ですが、異常な終了方法です。 一般的には反則なのでやむをえない場合のみ使用してください。

voodoo4500
質問者

補足

解答ありがとうございます。WM_DESTROYは知っていたんですが ご承知の通りやむをえない場合のみ使うものだと調べました。 またほかにもあるということはわかったんですがそれもやはり 異常な終了方法ということまでしかわかりませんでした。 やはりダイアログを何とかしなくてはならないのでしょうか?

関連するQ&A

  • ウインドウ終了の取得ができません

    以下にソースを #include <windows.h> #include <stdio.h> static int array[300] = {0}; static int temp[300] = {0}; static int count = 0; static int i = 0; BOOL CALLBACK EnumWindowProc(HWND hwnd, LPARAM lp) { static bool is_first = true; DWORD style = ::GetWindowLong(hwnd, GWL_STYLE); if ( ::IsWindow(hwnd) && ::IsWindowVisible(hwnd) && (style&WS_CAPTION) && !(style&WS_POPUP) ) { char buf[65536]; ::GetWindowText(hwnd, buf, 65535); if ( buf[0] != '\0' ){ if ( is_first ){ is_first = false; } else{ // 配列arrayにハンドルを代入 array[i] = int(hwnd) ; //printf("%d\n",i); i++; // 配列arrayに格納されたハンドル数 count++; } } } return TRUE; } int main(int argc, char** argv) { int a; int j = 0; int k = 0; int t_handend = 0; int flg = 0; char buf[65536]; // 無限ループ while(1){ // 起動しているアプリケーションのハンドル取得(配列arrayに格納) ::EnumWindows(EnumWindowProc, 0); i = 0; // temp内のハンドル数の計算 while(temp[t_handend] != 0){ t_handend++; } for(a=0;a<count;a++){ ::GetWindowText((HWND)array[a], buf, 65535); printf("array[%d]=%d=%s\n",a,array[a],buf); } for(a=0;a<t_handend;a++){ ::GetWindowText((HWND)temp[a], buf, 65535); printf("temp[%d]=%d=%s\n",a,temp[a],buf); } //printf("flg;%d\n",flg); for(k = 0; k < count; k++){ for(j = 0; j < t_handend; j++){ if(array[k] == temp[j]){ flg = 1; break; } } //printf("flg;%d\n",flg); if(flg != 1){ //printf("%d\n", array[i]); //プロセス名取得 ::GetWindowText((HWND)array[k], buf, 65535); printf("%sが起動しました\n", buf); //flg1=1; } flg = 0; } for(k = 0; k < t_handend ; k++){ for(j = 0; j < count; j++){ if(temp[k] == array[j]){ flg = 1; break; } } if(flg != 1){ ::GetWindowText((HWND)temp[k], buf, 65535); if((HWND)temp[k]!=0){ printf("%sが終了しました\n", buf); } //printf("%d\n", temp[i]); } flg = 0; } // tempの更新 for(j = 0; j < count; j++){ temp[j] = array[j]; } for(; j < 300; j++){ temp[j] = 0; } flg = 0; count = 0; puts(""); Sleep(3000); } return 0; } これでウインドが立ち上がったときと終了のログをとろうとしましたが、このままですと終了したウインドの名前がとれません。 どうしたらよいでしょうか。?

  • WM_CTLCOLORDLG

    WIN32、VC++2005で開発中です。 ダイアログが複数あり各々に違う背景色を着けたい場合、 下記のようなプログラムを書いたのですが、IF文の中に行けません。 「i」には0が入ってしまうんですが、なぜでしょうか? ほかにいい方法ありませんか? ボタンコントロールではちゃんと判別してくれました。 case WM_CTLCOLORDLG: i = GetWindowLong( (HWND)lParam, GWL_ID ); if ( i == IDD_ICHI_D ) { //位置出し画面描画 return (BOOL)CreateSolidBrush( RGB( 255,170,255 )); } break; WIN32初心者なのでなるべくわかりやすくご教授お願いします。

  • midiの再生が思うようにできません

    ファイルの文字列を1行ずつ読み込み、文字列の数字の範囲によって再生する音楽を変えるプログラムを作成していますが、読み込んだ文字列とは無関係に、ループの初めの範囲で指定してある音楽しか再生されません。読み込んだ文字列ごとに再生音楽を変えるにはどうすればいいのでしょうか?分かる方ご教授願います。 環境:WindowsXP, Visual C++ 2008 Express Edition 以下がプログラムのソースの一部です。 LRESULT CALLBACK WndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam) { FILE *fp; errno_t err; TCHAR buf[30]; TCHAR *temp; int m=0, n=0; switch(msg) { case WM_CREATE: CreateWindow(TEXT("BUTTON"), TEXT("Play"), WS_CHILD | WS_VISIBLE | BS_PUSHBUTTON,120, 100, 70, 70, hWnd, NULL, hInst, NULL); break; case WM_COMMAND: err = _tfopen_s(&fp, TEXT("C:\\Documents and Settings\\m22015\\My Documents\\Visual Studio 2008\\Projects\\process\\process\\Corner.txt"), TEXT("r+")); if(err != 0) break; temp = (TCHAR*)malloc(_tcsclen(buf)+1); if(temp == NULL){ MessageBox(hWnd, TEXT("Can't secure of memory"), TEXT("Error"), MB_OK); break; } for(int i=0; i<2; i++){ _fgetts(buf, 10, fp); _tcstok(buf, TEXT("\n")); } while(_fgetts(buf, 30, fp) != NULL){ _tcstok(buf, TEXT("\n")); _tcscpy(temp, buf); while(_stprintf(buf, _T("- { x:%d, y:%d }"), m, n)!=EOF){ if((m>=0 && m<110)&&(n>=0 && n<200)){ if(mciSendString(_T("play C+1.mid"), NULL, 0, NULL) != 0) { MessageBox(hWnd, _T("Can't play C+1.mid"), _T("Error"), MB_OK); SendMessage(hWnd, WM_CLOSE, 0, 0); } return 0; }else if((m>=110 && m<220)&&(n>=0 && n<200)){ if(mciSendString(_T("play D+1.mid"), NULL, 0, NULL) != 0) { MessageBox(hWnd, _T("Can't play D+1.mid"), _T("Error"), MB_OK); SendMessage(hWnd, WM_CLOSE, 0, 0); } return 0; }else if((m>=220 && m<330)&&(n>=0 && n<200)){ if(mciSendString(_T("play E+1.mid"), NULL, 0, NULL) != 0) { MessageBox(hWnd, _T("Can't play E+1.mid"), _T("Error"), MB_OK); SendMessage(hWnd, WM_CLOSE, 0, 0); } return 0; }else if((m>=330 && m<440)&&(n>=0 && n<200)){ if(mciSendString(_T("play F+1.mid"), NULL, 0, NULL) != 0) { MessageBox(hWnd, _T("Can't play F+1.mid"), _T("Error"), MB_OK); SendMessage(hWnd, WM_CLOSE, 0, 0); } return 0; }else if((m>=440 && m<550)&&(n>=0 && n<200)){ if(mciSendString(_T("play G+1.mid"), NULL, 0, NULL) != 0) { MessageBox(hWnd, _T("Can't play G+1.mid"), _T("Error"), MB_OK); SendMessage(hWnd, WM_CLOSE, 0, 0); } return 0; }else if((m>=550 && m<660)&&(n>=0 && n<200)){ if(mciSendString(_T("play A+1.mid"), NULL, 0, NULL) != 0) { MessageBox(hWnd, _T("Can't play A+1.mid"), _T("Error"), MB_OK); SendMessage(hWnd, WM_CLOSE, 0, 0); } return 0; }else if((m>=660 && m<770)&&(n>=0 && n<200)){ if(mciSendString(_T("play B+1.mid"), NULL, 0, NULL) != 0) { MessageBox(hWnd, _T("Can't play B+1.mid"), _T("Error"), MB_OK); SendMessage(hWnd, WM_CLOSE, 0, 0); } return 0; }else if(mciSendString(_T("play C.mid"), NULL, 0, NULL) != 0) { MessageBox(hWnd, _T("Can't play C.mid"), _T("Error"), MB_OK); SendMessage(hWnd, WM_CLOSE, 0, 0); } return 0; }else if((m>=110 && m<220)&&(n>=200 && n<400)){ if(mciSendString(_T("play D.mid"), NULL, 0, NULL) != 0) { MessageBox(hWnd, _T("Can't play D.mid"), _T("Error"), MB_OK); SendMessage(hWnd, WM_CLOSE, 0, 0); } return 0; 以下省略 . . . }else{ break; } } } free(temp); fclose(fp); break; case WM_CLOSE: DestroyWindow(hWnd); break; case WM_DESTROY: PostQuitMessage(0); break; default: return (DefWindowProc(hWnd, msg, wParam, lParam)); } return 0; }

  • DialogBox

    こんばんは 最近Windowsプログラムでツールを作ることになりまして 久しぶりにダイアログボックスを作成しようとして、いきなり躓きました;; DialogBox関数でダイアログを表示できないのですが、何か特別な処理って必要でしたっけ? 以下ソースコードです #include <windows.h> #include "resource.h" BOOL CALLBACK DialogProc(HWND, UINT, WPARAM, LPARAM); int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, PSTR lpCmdLine, int nCmdShow ) { DialogBox(hInstance, MAKEINTRESOURCE("IDD_DIALOG"), NULL, (DLGPROC)DialogProc); return 0; } BOOL CALLBACK DialogProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam) { switch (msg) { case WM_INITDIALOG: // ダイアログボックスが作成されたとき return TRUE; case WM_CLOSE: EndDialog(hWnd, IDOK); return TRUE; } return FALSE; } よろしくお願いします

  • WM_CREATE について

    Windows API の勉強を始めた者です。 CreateWindow関数を使ったときに発行されるWM_CREATEについて質問させていただきます。 以下のようなプログラムを作りました。このプログラムはウインドウを作るプログラムなのですが、はじめにウインドウを作るかどうかをWindowProcの中で聞いています。 このプログラムでウインドウを作らないという選択肢をとった時が分かりません。 WindowProcでは return -1 をするのでウインドウは作られず、従ってhWndにはNULLが入ります。そして次の文で、  if (hWnd == NULL) {   MessageBox(NULL,TEXT("CreateWindow failed"),NULL,MB_OK);   return 0;  } メッセージボックスが表示されてからプログラムが終了すると思ったのですが、実際にはメッセージボックスは表示されませんでした。 なぜでしょうか。return -1 をした時点で、ウインドウが作られないのでWM_DESTROYがウインドウプロシージャにSendされるのかと考えたのですが、そうなのでしょうか。 よろしくお願いします。 /* 作ったプログラム */ #include <windows.h> LRESULT CALLBACK WindowProc (HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam) {  int YESNO;  switch(uMsg) {  case WM_DESTROY:   PostQuitMessage(0);  return 0;  case WM_CREATE:  YESNO = MessageBox(NULL, TEXT("Create a new window?"),        ((LPCREATESTRUCT)lParam)->lpszName, MB_YESNO);  if (YESNO == IDYES)   return 0;  if (YESNO == IDNO)   return -1;  }  return DefWindowProc(hWnd, uMsg, wParam, lParam); } int WINAPI WinMain(HINSTANCE hInstance,           HINSTANCE hPrevInstance,           PSTR lpCmdLine,            int nCmdShow) {  WNDCLASS wc;  ATOM atom;  MSG msg;  HWND hWnd;  wc.style = CS_HREDRAW| CS_VREDRAW;  wc.lpfnWndProc = WindowProc;  wc.cbClsExtra = 0;  wc.cbWndExtra = 0;  wc.hInstance = hInstance;  wc.hIcon = NULL;  wc.hCursor = NULL;  wc.hbrBackground = (HBRUSH)COLOR_BACKGROUND + 1;  wc.lpszMenuName = NULL;  wc.lpszClassName = TEXT("sample_window");  if ((atom = RegisterClass(&wc)) == 0) {   MessageBox(NULL,TEXT("RegisterClass failed"),NULL,MB_OK);   return 0;  }  hWnd = CreateWindow((LPCTSTR)atom, TEXT("Sampe window"),              WS_OVERLAPPEDWINDOW | WS_VISIBLE,              100, 100, 400, 300,              NULL, NULL, hInstance, NULL);                if (hWnd == NULL) {   MessageBox(NULL,TEXT("CreateWindow failed"),NULL,MB_OK);   return 0;  }  while (GetMessage(&msg, NULL, 0, 0) > 0) {   DispatchMessage(&msg);  }  return msg.wParam; }

  • 何処が間違っていますか?

    ---------------------------------------------------------------------------------------- #include<stdio.h> #include<stdlib.h> #define MAX_LINE 128 int main(void); int main(void) { char buf[MAX_LINE]; int n; printf("降水確率を入力してください。\n"); gets(buf); n = atoi(buf); printf("降水確率は %d %% です。\n",n); if (n >= 50) { printf("傘を忘れずにね。\n"); } else { printf(傘はいりません。\n"); } printf("いってらっしゃい。\n"); return(0); }

  • Type name expected エラーがでます。

    こんにちは。 非常に短い 次のコードで、 Type name expected エラーが出ます。 何か悪いのでしょうか。 コンパイラは、bcc55 (ボーランドのコマンドライン用の 無償のコンパイラです)。 #include <windows.h> #include "dialog1.h" BOOL CALLBACK dialogProc(HWND,UINT,WPARAM,LPARAM); int WINAPI WinMain(HINSTANCE h,HINSTANCE,LPSTR,int) { DialogBox(h,"DIALOG1",HWND_DESKTOP,(DLGPROC)dialogProc); return 0; } BOOL CALLBACK dialogProc(HWND hw,UINT msg,WPARAM wp,LPALAM lp){ return FALSE; } 何か分かる人がいましたら、 よろしくお願いします。 dialog1.cpp-------------------------------------- #include <windows.h> #include "dialog1.h" DIALOG1 DIALOG 100,100,200,80 STYLE DS_MODALFRAME | WS_POPUP | WS_VISIBLE | WS_CAPTION | WS_SYSMENU CAPTION "FIRST DIALOG" FONT 10,"system" { DEFPUSHBUTTON "BEEP",ID_0,25,10,50,15 PUSHBUTTON "EXIT",ID_1,25,30,50,15 } dialog1.h----------------------------- #define ID_0 100 #define ID_1 101

  • CSVを用いた検索プログラム動かし方

    #pragma warning( disable: 4996 ) #include <stdio.h> #include <string.h> #include <fstream> using namespace std; typedef struct tagKOTOWAZA{ char japanese[50]; char english[50]; }KOTOWAZA; int main() { char buf[256]; KOTOWAZA c[200]; int i, count; /*ifstream strtok strcpy を使ってファイルを読み込む*/ //=====ここから===== ifstream fin("Book1.csv"); if(fin.is_open()){ //ファイル内容の表示とクローズ for(count=0;fin.getline(buf, sizeof(buf)), !fin.eof();count++){//読み込める間 //printf("%s",buf);デバッグ用 char *p; p = strtok(buf,","); if(p)strcpy(c[count].japanese,p); p = strtok(NULL,","); if(p)strcpy(c[count].english,p); } fin.close(); }else{ printf("ファイルのオープンに失敗しました。\n"); return 1; } //=====ここまで==== return 0; } ここからどうすればCSVファイルに書いた 漢字,English を検索できるのかがわかりません・・・ 言語はC++を使っていますvisualstudio2012を使っています。 どうすればいいのか全く分かりません。 よろしくお願いします。

  • マウスフックについて

    Dllにてマウスフックをして、左ボタンが押しあがったらWM_LBUTTONUPされたら メッセージを送信するというものです。 そのときに、マウスの位置はどこにあってもいいのです。 たとえば、自分のウインドウの中で左ボタンを押して、 デスクトップ上などで左ボタンがあがったらメッセージを送信するというようにしたいのですがうまくいきません。 以下がソースです。 よろしくお願いします。 #include <windows.h> #include "MouseHook.h" HINSTANCE hInst; HHOOK hHook; HWND hWnd; BOOL bHook; int WINAPI DllMain(HINSTANCE hInstance, DWORD fdReason, PVOID pvReserved) { hInst = hInstance; return TRUE; } EXPORT int SetMainHWND(HWND hMainWindow) { hWnd = hMainWindow; return 0; } EXPORT BOOL IsHooking() { if (bHook) return TRUE; else return FALSE; } EXPORT int MouseHookSet() { hHook = SetWindowsHookEx(WH_MOUSE, (HOOKPROC)MouseHookProc,hInst, NULL); if (hHook == NULL) { return -1; } else { bHook = TRUE; return 0; } } EXPORT int MouseHookEnd() { if (UnhookWindowsHookEx(hHook) != 0) { bHook = FALSE; return 0; } else { return -1; } } EXPORT LRESULT CALLBACK MouseHookProc(int nCode, WPARAM wParam, LPARAM lParam) { MOUSEHOOKSTRUCT *pmh; pmh = (MOUSEHOOKSTRUCT *)lParam; if (wParam == WM_LBUTTONUP) { SendMessage(hWnd,MOUSEHOOK_LBUTTONUP,0,0); } if (wParam == WM_NCLBUTTONUP) { SendMessage(hWnd,MOUSEHOOK_LBUTTONUP,0,0); } return CallNextHookEx(hHook,nCode,wParam,lParam); }

  • ウィンドウが表示されない

    あるサンプルプログラムを改造しようとしているのですが、g_hWnd=CreateWindow( _T(__FILE__),_T("シューティングゲーム"),WINDOW_STYLE, CW_USEDEFAULT,CW_USEDEFAULT,rc.right-rc.left,rc.bottom-rc.top, NULL,NULL,hInst,NULL);のところのWINDOW_STYLEをWS_OVERLAPPEDWINDOWに変えたらウィンドウが表示されません。どうしたら表示されるのでしょうか。わかる方いらいしたらご教授お願いします。多分ここだろうなというところのコードを載せます。 LRESULT CALLBACK MainWndProc(HWND hWnd,UINT msg,WPARAM wParam,LPARAM lParam) { switch(msg) { case WM_KEYDOWN: switch(wParam) { case VK_F1: ChangeDisplayMode(); return 0; case VK_ESCAPE: PostMessage(hWnd,WM_CLOSE,0,0); return 0; } return 0; case WM_DISPLAYCHANGE: // IDirect3DDevice9::Reset メソッドから Send される DisplayChange(); return 0; case WM_SIZE: if(g_bWndMode==false || wParam==SIZE_MINIMIZED) return 0; g_D3DPP.BackBufferWidth = LOWORD(lParam); g_D3DPP.BackBufferHeight = HIWORD(lParam); if(wParam==SIZE_MAXIMIZED || wParam==SIZE_RESTORED) ChangeWindowSize(); return 0; case WM_ACTIVATE: g_bActive=(LOWORD(wParam)!=WA_INACTIVE); return 0; case WM_DESTROY: CleanupD3DObject(); CleanupDXGraphics(); PostQuitMessage(0); return 0; } return DefWindowProc(hWnd,msg,wParam,lParam); }

専門家に質問してみよう