CWindowImpl を使用したウィンドウの実装

ウィンドウを実装するには、CWindowImpl からクラスを派生させます。 派生クラスで、メッセージ マップとメッセージ ハンドラー関数を宣言します。 これで、次の 3 つの方法でクラスを使用できるようになりました。

新しい Windows クラスに基づくウィンドウの作成

CWindowImpl には、Windows クラス情報を宣言するための DECLARE_WND_CLASS マクロが含まれています。 このマクロは CWndClassInfo を使用して新しい Windows クラスの情報を定義する GetWndClassInfo 関数を実装します。 CWindowImpl::Create が呼び出されると、この Windows クラスが登録され、新しいウィンドウが作成されます。

Note

CWindowImpl により DECLARE_WND_CLASS マクロに NULL が渡されます。これは、ATL によって Windows クラス名が生成されることを意味します。 独自の名前を指定するには、お使いの CWindowImpl 派生クラスの DECLARE_WND_CLASS に文字列を渡します。

例: ウィンドウを実装する

新しい Windows クラスに基づいてウィンドウを実装するクラスの例を次に示します。

class CMyCustomWnd : public CWindowImpl<CMyCustomWnd>
{
public:
   // Optionally specify name of the new Windows class
   DECLARE_WND_CLASS(_T("MyName")) 
              // If this macro is not specified in your
              // class, ATL will generate a class name

   BEGIN_MSG_MAP(CMyCustomWnd)
      MESSAGE_HANDLER(WM_PAINT, OnPaint)
   END_MSG_MAP()

   LRESULT OnPaint(UINT /*nMsg*/, WPARAM /*wParam*/, LPARAM /*lParam*/, 
      BOOL& /*bHandled*/)
   {
      // Do some painting code
      return 0;
   }

};

ウィンドウを作成するには、CMyWindow のインスタンスを作成してから、Create メソッドを呼び出します。

Note

既定の Windows クラス情報をオーバーライドするには、CWndClassInfo メンバーを適切な値に設定して派生クラスで GetWndClassInfo メソッドを実装します。

既存の Windows クラスをスーパークラスにする

DECLARE_WND_SUPERCLASS マクロを使用すると、既存の Windows クラスをスーパークラスにするウィンドウを作成できます。 CWindowImpl 派生クラスでこのマクロを指定します。 他の ATL ウィンドウと同様に、メッセージはメッセージ マップによって処理されます。

DECLARE_WND_SUPERCLASS を使用すると、新しい Windows クラスが登録されます。 この新しいクラスは、指定した既存のクラスと同じになりますが、ウィンドウ プロシージャは CWindowImpl::WindowProc (またはこのメソッドをオーバーライドする関数) に置き換えられます。

例: Edit クラスをスーパークラスにする

次に、標準の Edit クラスをスーパークラスにするクラスの例を示します。

class CMyEdit : public CWindowImpl<CMyEdit>
{
public:
   // "Edit" is the name of the standard Windows class.
   // "MyEdit" is the name of the new Windows class
   // that will be based on the Edit class.
   DECLARE_WND_SUPERCLASS(_T("MyEdit"), _T("Edit"))

   BEGIN_MSG_MAP(CMyEdit)
      MESSAGE_HANDLER(WM_CHAR, OnChar)
   END_MSG_MAP()

   LRESULT OnChar(UINT /*nMsg*/, WPARAM /*wParam*/, LPARAM /*lParam*/, 
      BOOL& /*bHandled*/)
   {
      // Do some character handling code
      return 0;
   }
};

スーパークラスになった Edit ウィンドウを作成するには、CMyEdit のインスタンスを作成してから、Create メソッドを呼び出します。

既存のウィンドウをサブクラスにする

既存のウィンドウをサブクラスにするには、前の 2 つのケースのように、CWindowImpl からクラスを派生させ、メッセージ マップを宣言します。 ただし、既に存在するウィンドウをサブクラスにするため、Windows クラスの情報は指定しないことにご注意ください。

Create を呼び出すのではなく、SubclassWindow を呼び出して、サブクラスにする既存のウィンドウへのハンドルを渡します。 ウィンドウがサブクラス化されたら、CWindowImpl::WindowProc (またはこのメソッドをオーバーライドする関数) を使用してメッセージをメッセージ マップに送信します。 サブクラス ウィンドウをオブジェクトからデタッチするには、UnsubclassWindow を呼び出します。 ウィンドウの元のウィンドウ プロシージャが復元されます。

関連項目

ウィンドウの実装