クリックしたデータを修正する



VC++ で DialogBox の Edit を利用して、マウスで左クリックされたデータを修正します。

前田稔(Maeda Minoru)の超初心者のプログラム入門

プロジェクトの作成

  1. 新規プロジェクトからテンプレートを使って(NumEdit)を作成して下さい。
  2. ソースファイルを表示します。
    NumEdit.cpp を表示して「// グローバル変数 :」の位置までスクロールして下さい。
        // グローバル変数:
        HINSTANCE hInst;                          // 現在のインスタンス
        TCHAR szTitle[MAX_LOADSTRING];            // タイトル バー テキスト
        TCHAR szWindowClass[MAX_LOADSTRING];      // タイトル バー テキスト
        int         DATA[30];                     // 修正対象のデータ
        POINT       pt= { 0,0 };                  // クリックした座標
        int         NUM= 0;                       // クリックした DATA 番号
        
  3. 「このコード モジュールに含まれる関数の前宣言」を表示して、次のプロトタイプ宣言を追加して下さい。
        void                ShowData(HDC);
        void                Keisen(HDC);
        int                 ItemNo(POINT);
        
  4. BOOL InitInstance( ) を表示します。
    Windows サイズを 800,220 に設定して下さい。
        hWnd = CreateWindow(szWindowClass, szTitle, WS_OVERLAPPEDWINDOW,
               CW_USEDEFAULT, CW_USEDEFAULT, 800, 220, NULL, NULL, hInstance, NULL);
        
  5. CALLBACK WndProc( ) を表示します。
    WM_CREATE: を追加して DATA[] に1~30までの値を格納します。
        case WM_CREATE:
            for(NUM=0; NUM<30; NUM++)     DATA[NUM]= NUM+1;
            break;
        
  6. WM_LBUTTONDOWN: を追加してマウスの左ボタンをキャッチします。
    POINT 構造体にクリックされた座標を格納します。
    ItemNo() で座標から該当する DATA[] 配列の番号を計算します。
    InvalidateRect() と UpdateWindow() で WM_PAINT に制御をわたします。
        case WM_LBUTTONDOWN:
            pt.x= LOWORD(lParam);
            pt.y= HIWORD(lParam);
            NUM= ItemNo(pt);
            InvalidateRect(hWnd,NULL,TRUE);
            UpdateWindow(hWnd);
            break;
        
  7. WM_PAINT: では ShowData(hdc) で画面を描画します。
        case WM_PAINT:
            hdc = BeginPaint (hWnd, &ps);
            // TODO: この位置に描画用のコードを追加してください...
            ShowData(hdc);
            EndPaint( hWnd, &ps );
            break;
        
  8. 数字一覧を表示する関数です。
    ソースプログラムの最後に追加して下さい。
        //★ 数字一覧を表示する
        void    ShowData(HDC hdc)
        {   int         n;
            char        str[40];
    
            Keisen(hdc);
            for(n=0; n<30; n++)
            {   wsprintf(str,"%5d",DATA[n]);
                TextOut(hdc,(n%10)*70+50,n/10*28+60,str,5);
            }
            wsprintf(str,"x=%4d  y=%4d  n=%4d",pt.x,pt.y,NUM);
            TextOut(hdc,10,10,str,strlen(str));
        }
        
  9. 罫線を引く関数です。
    使用するフォントと環境に合わせて罫線の幅と高さを調節して下さい。
        //★ 罫線を引く
        void    Keisen(HDC hdc)
        {   HPEN        hPen;
            USHORT      i;
    
            hPen= CreatePen(PS_SOLID,3,RGB(180,180,180));   // ソリッドペンの作成
            SelectObject(hdc,hPen);                         // hPen を選択
            for(i=0; i<4; i++)
            {   MoveToEx(hdc,26,i*28+57,NULL);              // 開始点に移動
                LineTo(hdc,725,i*28+57);                    // 罫線を引く
            }
            for(i=0; i<11; i++)
            {   MoveToEx(hdc,i*70+26,57,NULL);
                LineTo(hdc,i*70+26,140);
            }
        }
        
  10. クリック位置のアイテム番号を計算する関数です。
        //★ クリック位置のアイテム番号を知る
        int     ItemNo(POINT pt)
        {
            return((pt.x-26)/70+((pt.y-57)/28*10));
        }
        
  11. ビルド(コンパイル)に続いて実行を行います。
    罫線で囲まれた数字をクリックすると、座標と番号が表示されます。
    番号は DATA[] の添え字なので、表示されている数字より1少ない値になります。

Dialog Box を設定して完成させる

  1. ページ先頭の画像を参考にして DialogBox を作成します。
    [EditControl] と [Button] を配置して下さい。
    種類 ID 種類 キャプション
    DialogBox IDD_DIALOG1 修正ボックス
    EditControl IDC_EDIT1
    Button IDOK OK
    Button IDCANCEL キャンセル
  2. Prototype 宣言に DialogProc() を追加します。
        LRESULT CALLBACK    DialogProc(HWND, UINT, WPARAM, LPARAM);
        void                ShowData(HDC);
        void                Keisen(HDC);
        int                 ItemNo(POINT);
        
  3. WM_LBUTTONDOWN: に DialogBox を表示するコードを追加します。
        case WM_LBUTTONDOWN:
            pt.x= LOWORD(lParam);
            pt.y= HIWORD(lParam);
            NUM= ItemNo(pt);
            DialogBox(hInst,MAKEINTRESOURCE(IDD_DIALOG1),NULL,(DLGPROC)DialogProc);
            InvalidateRect(hWnd,NULL,TRUE);
            UpdateWindow(hWnd);
            break;
        
  4. DialogBox の Call Back 関数です。
    OK ボタンがクリックされたときに IDC_EDIT1 からデータを取得して DATA[NUM] に格納します。
        //★ DialogBox Call Back 関数 
        LRESULT CALLBACK DialogProc(HWND hDlg,UINT msg,WPARAM wp,LPARAM lp)
        {   char    buf[24];
    
            switch(msg)
            {   case WM_COMMAND:
                    switch(LOWORD(wp))
                    {   case IDOK:
                            if (NUM>=0 && NUM<30)
                            {   GetDlgItemText(hDlg,IDC_EDIT1,buf,sizeof(buf));
                                DATA[NUM]= atoi(buf);
                            }
                            EndDialog(hDlg, IDOK);
                            return TRUE;
                        case IDCANCEL:
                            EndDialog(hDlg, IDCANCEL);
                            return TRUE;
                    }
                    break;
                case WM_CLOSE:
                    EndDialog(hDlg, TRUE); 
                    return TRUE;
                    break;
            }
            return FALSE;
        }
        

超初心者のプログラム入門(Win32API C++)