レガシー Windows API(概要)について

ここで紹介しているAPIは、Windows95、Windows NT3.5時代のAPI群であり、最新のAPIは含まれていないことに注しして欲しい。なお、当時の解説書は現在よりもより詳細に解説しているため、参考になるはずである。

  • レイアウトを変換する際、崩れているページがあります。
  • 概要およびSampleコードはありますが、APIの解説はありません。

ご要望があれば旧版のWin32 API(HELP形式)をお譲りします。問い合わせフォームより申し込みください。

ウィンドウの概要

Microsoft(R) Windows(TM) オペレーティング システム用に記述されているアプリケーションでは、 アプリケーションが出力を表示したりユーザーからの入力を受け取ったりする画面上の長方形の領域のことを、 ウィンドウと呼んでいます。ウィンドウは、 アプリケーション自身やほかのアプリケーションのウィンドウと画面を共有します。ユーザーから入力を受け取ることのできるウィンドウは、 一度に1つだけです。ユーザーは、 マウスやキーボードなどの入力デバイスを使って、 ウィンドウやウィンドウを所有するアプリケーションと対話をすることができます。

ウィンドウは、Windowsベースのアプリケーションがユーザーと対話して作業を実行するための唯一の手段です。このため、 Windowsベースのアプリケーションが最初に行う作業は、 ウィンドウを作成する作業になります。このトピックでは、 Microsoft(R) Win32(R)アプリケーション プログラミング インターフェイス (API) 要素について説明します。アプリケーションは、 ウィンドウの作成、 複数のウィンドウ間の親子関係や順序関係などの管理、 ウィンドウのサイズ変更、 移動、 表示などを行うために、 これらのAPI要素を使います。

次の各トピックでは、 ウィンドウについて説明します。

デスクトップ ウィンドウ

アプリケーション ウィンドウ

ウィンドウの作成

ウィンドウ ハンドル

ウィンドウ スタイル

所有されているウィンドウ

使用不能のウィンドウ

前景ウィンドウおよび背景ウィンドウ

表示状態

ウィンドウのサイズと位置

ウィンドウの破棄

メイン ウィンドウの作成方法

子ウィンドウの作成、 列挙、 およびサイズ変更の方法

ウィンドウを破棄する方法

ウィンドウ関数とメッセージ

 

デスクトップ ウィンドウ

Windowsは、 起動時にデスクトップ ウィンドウを自動的に作成します。「デスクトップ ウィンドウ」とは、 画面の背景を描画し、 Win32ベースのすべてのアプリケーションによって表示されるすべてのウィンドウの基底部分となる、 システム定義のウィンドウのことです。

デスクトップ ウィンドウは、 ビットマップ ファイル (ファイル名拡張子.BMP) として格納されているビットマップを使用して、 画面の背景を描画します。ビットマップにより作成されるパターンは、 「(デスクトップの) 壁紙」と呼ばれます。デフォルトでは、 デスクトップ ウィンドウは、 次のレジストリのキーの中で指定されているファイルのビットマップを壁紙として使用します。 

HKEY_CURRENT_USER\Control Panel\Desktop\Wallpaper

コントロール パネル アプリケーションなど、 システム設定を行うアプリケーションは、 SetDeskWallpaper関数を使って別のビットマップ ファイル名を指定することにより、 壁紙を変更できます。SetDeskWallpaperは、 指定されたファイルからビットマップをロードし、 そのビットマップを使って画面の背景を描画します。そして、 新しいファイル名をレジストリのWallpaperキーに設定します。ビットマップについては、 詳細はビットマップの概要を、 レジストリについてはレジストリと初期化ファイルの概要を参照してください。

アプリケーション ウィンドウ

すべてのWin32ベースのアプリケーションは、 アプリケーションの主要なウィンドウとして動作する、 「メイン ウィンドウ」という最低1つのウィンドウを作成します。このウィンドウは、 ユーザーとアプリケーションとの主要なインターフェイスとして動作します。ほとんどのアプリケーションは、 メイン ウィンドウのほかにも多くのウィンドウを直接的または間接的に作成して、 メイン ウィンドウに関連する作業を実行します。各ウィンドウは、 出力を表示したり、 ユーザーからの入力を受け取ったりする役割を持ちます。

アプリケーション ウィンドウの構成要素

アプリケーション ウィンドウには、 タイトル バー、 コントロール メニュー (システム メニューとも呼ばれる)、 アイコン化ボタン、 最大表示ボタン、 サイズ変更境界、 クライアント領域、 水平スクロール バー、 および垂直スクロール バーを組み込むことができます。通常、 アプリケーションのメイン ウィンドウには、 これらの構成要素がすべて含まれています。次の図は、 典型的なメイン ウィンドウの構成要素を示したものです。

「タイトル バー」には、 アプリケーション定義のアイコンとテキスト行が表示されます。通常は、 アプリケーションの名前やウィンドウの使用目的などが表示されます。アプリケーションは、 ウィンドウの作成時にこのアイコンとテキストを指定できます。また、 タイトル バーは、 ユーザーがマウスなどのポインティング デバイスを使ってウィンドウを移動するときにも使われます。

ほとんどのアプリケーションには、 アプリケーションがサポートしているコマンドを一覧表示するメニューが含まれています。メニュー内の各項目は、 コマンドの主要なカテゴリを表しています。メニュー バーから項目を選ぶと、 通常はポップアップ メニューがオープンされます。このポップアップ メニューには、 指定のカテゴリに属する作業に対応したコマンド項目が表示されます。ユーザーはコマンドを選択することにより、 その作業を実行するようアプリケーションに指示します。

コントロール メニュー ボックスは、 クリックしたときにコントロール メニューを表示するビットマップです。コントロール メニューは、 Windowsが作成し、 管理します。ユーザーがこのメニューを選ぶと、 ウィンドウのサイズや位置の設定、 アプリケーションのクローズ、 Windowsのタスク リスト([アプリケーションの切り替え])などの機能を持つ標準的なメニュー項目が表示されます。メニューおよびコントロール メニューについて詳しくは、 メニューの概要を参照してください。

アイコン化ボタンと最大表示ボタンは、 それぞれクリックしたときにウィンドウのサイズや位置に作用するビットマップです。ユーザーが「最大表示ボタン」をクリックすると、 Windowsはウィンドウのサイズを画面いっぱいに拡大し、 ウィンドウの位置を調節します。またこのとき、 Windowsは最大表示ボタンを復元ボタン ([元のサイズに戻す]ボタン) に置き換えます。「復元ボタン」とは、 クリックしたときにウィンドウのサイズを元のサイズと位置に戻すビットマップのことです。

ユーザーが「アイコン化ボタン」をクリックすると、 Windowsはウィンドウのサイズをアイコンのサイズにまで縮小し、 ウィンドウの位置を画面の下部に設定して、 そこにウィンドウのアイコンを表示します。アイコンとは、 ウィンドウを表す32×32ピクセルのビットマップのことです。アイコンについて詳しくは、 アイコンの概要を参照してください。

「サイズ変更境界」とは、 ウィンドウの周りの線状の領域のことです。ユーザーはこの境界をマウスなどのポインティング デバイスを使ってドラッグすることにより、 ウィンドウのサイズを変更することができます。

「クライアント領域」とは、 アプリケーションがテキストやグラフィックなどの出力を表示させるウィンドウ内の領域部分のことです。たとえば、 デスクトップ パブリッシング (DTP) アプリケーションでは、 現在作業中の文書中のページが、 クライアント領域に表示されます。アプリケーションは、 ウィンドウに送られる入力を処理し、 クライアント領域に出力を表示するために、 ウィンドウ プロシージャと呼ばれる関数を提供しなければなりません。ウィンドウ プロシージャについて詳しくは、 ウィンドウ プロシージャの概要を参照してください。

水平および垂直スクロール バーは、 マウスやキーボードからの入力を、 クライアント領域の内容を水平または垂直の方向の移動量に変換します。たとえば、 ワード プロセッシング アプリケーションで1画面に表示しきれないような長い文書を扱う場合は、 垂直スクロール バーを提供して、 ユーザーが文書をページ単位で移動させることができるようにしています。

タイトル バー、 メニュー バー、 コントロール メニュー、 アイコン化ボタン、 最大表示ボタン、 サイズ変更境界、 およびスクロール バーを総称して、 ウィンドウの「非クライアント領域」と呼びます。Windowsは、 非クライアント領域のほとんどのアスペクトを管理しています。逆に言えば、 ウィンドウのそのほかの部分については、 アプリケーションが管理することになります。特に、 アプリケーションはクライアント領域の外観と動作を管理します。

 

コントロール、 ダイアログ ボックス、 メッセージ ボックス

アプリケーションは、 メイン ウィンドウのほかに、 コントロールやダイアログ ボックス、 メッセージ ボックスなど、 何種類かのウィンドウを使います。

コントロールとは、 オープンするファイルの名前、 テキストの選択項目に適用させる望ましいポイント サイズなどの具体的な情報を、 アプリケーションがユーザーから得るために使用する、 ウィンドウのことです。コントロールは、 アプリケーションの特定の機能の制御に必要な情報を得る場合にも使われます。たとえば、 通常のワード プロセッシング アプリケーションは、 単語の折り返し機能のオンまたはオフの切り替えをユーザーに選んでもらうために、 コントロールを提供します。コントロールについて詳しくは、 コントロールの概要、 ボタンの概要、 リスト ボックスの概要、 エディット コントロールの概要、 コンボ ボックスの概要、 スクロール バーの概要、 およびスタティック コントロールの概要を参照してください。

コントロールは常にほかのウィンドウと組み合わせて使われます。ふつうは、 ダイアログ ボックスと組み合わせて使われます。ダイアログ ボックスは、 1つまたは複数のコントロールを持つウィンドウです。アプリケーションは、 コマンドの実行に必要な入力をユーザーに促す場合に、 ダイアログ ボックスを使います。たとえば、 ファイルを開くコマンドを持つアプリケーションであれは、 パスとファイル名をユーザーに入力してもらうためのコントロールを持つダイアログ ボックスを表示します。

メッセージ ボックスとは、 ユーザーに対して確認や注意、 警告などを表示するウィンドウのことです。たとえば、 メッセージ ボックスを使って、 アプリケーションが作業中に遭遇した問題をユーザーに知らせることができます。

通常、 ダイアログ ボックスとメッセージ ボックスは、 メイン ウィンドウと同じ構成要素を使うことはありません。ほとんどの場合、 これらのボックスは、 タイトル バー、 コントロール メニュー、 境界 (サイズ変更はできない)、 およびクライアント領域で構成されます。しかし、 メニュー バー、 アイコン化ボタン、 最大表示ボタン、 スクロール バーなどは持たないのがふつうです。ダイアログ ボックスとメッセージ ボックスについて詳しくは、 ダイアログ ボックスの概要を参照してください。

 

ウィンドウの作成

アプリケーションは、 CreateWindow関数またはCreateWindowEx関数を使ってメイン ウィンドウを作成し、 ウィンドウの属性の定義に必要な情報をWindowsに提供します。CreateWindowEx関数にはCreateWindow関数にはないdwExStyleというパラメータがありますが、 それ以外のパラメータはまったく同じです。実際、 CreateWindowdwExStyleを0に設定して単にCreateWindowExを呼び出しているにすぎません。このため、 このトピックではCreateWindowEx関数のみについて説明します。

Win32 APIでは、 ダイアログ ボックスやメッセージ ボックスなど、 特殊な目的に使うウィンドウを作成するための関数として、 DialogBox、 CreateDialog、 MessageBoxといった関数が用意されています。これらの関数について詳しくは、 ダイアログ ボックスの概要を参照してください。

 

ウィンドウの属性

アプリケーションは、 ウィンドウの作成時に次の情報を提供しなければなりません。

  • ウィンドウ クラス

  • ウィンドウ名

  • ウィンドウ スタイル

  • 親ウィンドウまたはオーナー ウィンドウ

  • 位置、 サイズ、 Z順序 (配置順序)

  • 子ウィンドウIDまたはメニュー ハンドル

  • インスタンス ハンドル

  • 作成データ

これらの属性について、 次の各項目でそれぞれ説明します。

 

ウィンドウ クラス

すべてのウィンドウは、 あるウィンドウ クラスに属します。アプリケーションは、 そのクラスのウィンドウを作成する前に必ずウィンドウ クラスを登録しなければなりません。ウィンドウ クラスとは、 ウィンドウの外観と動作を定義するものです。ウィンドウ クラスの主な構成要素はウィンドウ プロシージャです。これは、 ウィンドウに送られてくるすべての入力および要求を受け取り、 それらを処理する関数です。Windowsは、 これらの入力や要求をメッセージの形でアプリケーションに提供します。ウィンドウ クラス、 ウィンドウ プロシージャ、 メッセージについて詳しくは、 ウィンドウ クラスの概要、 ウィンドウ プロシージャの概要、 メッセージとメッセージ キューの概要を参照してください。

 

ウィンドウ名

ウィンドウには名前を付けることができます。「ウィンドウ名 (ウィンドウ テキストとも呼ばれる)」とは、 ユーザーがウィンドウを識別できるようにするためのテキスト文字列のことです。通常、 メイン ウィンドウ、 ダイアログ ボックス、 またはメッセージ ボックスがタイトル バーを持つ場合は、 そこにウィンドウ名が表示されます。コントロールの場合には、 ウィンドウ名の表示はコントロールのクラスにより異なります。ボタン、 エディット コントロール、 またはスタティック コントロール (表示させる場合) では、 コントロール内の長方形領域にウィンドウ名が表示されます。リスト ボックス、 コンボ ボックス、 またはスタティック コントロールでは、 ウィンドウ名は表示されません。

ウィンドウ名を変更するには、 ウィンドウの作成後にSetWindowText関数を使います。現在のウィンドウ名テキストをウィンドウから取得するには、 GetWindowTextLength関数とGetWindowText関数を使います。

 

ウィンドウ スタイル

すべてのウィンドウは、 1つまたはそれ以上のウィンドウ スタイルを持ちます。「ウィンドウ スタイル」とは、 ウィンドウ クラスでは指定できないようなウィンドウの外観や動作を定義する、 名前付きの定数のことです。たとえば、 SCROLLBARクラスはスクロール バー コントロールを作成しますが、 SBS_HORZおよびSBS_VERTの各スタイルは、 作成されるスクロール バー コントロールが水平または垂直のどちらのスクロール バーなのかを決定します。すべてのウィンドウに対して適用できるスタイルもいくつかありますが、 ほとんどのスタイルは特定のウィンドウ クラスを持つウィンドウに対してだけ適用できます。Windowsはスタイルを解釈します。また、 指定のクラスのウィンドウ プロシージャも、 ある程度までスタイルを解釈します。

 

親ウィンドウまたはオーナー ウィンドウ

ウィンドウには親ウィンドウを持たせることができます。親ウィンドウを持つウィンドウは、 「子ウィンドウ」と呼ばれます。「親ウィンドウ」は、 子ウィンドウの位置決めの際に使われる座標系を提供します。親ウィンドウを持つことで、 ウィンドウの外観が影響を受けます。たとえば、 子ウィンドウをクリップして、 その親ウィンドウの境界内に子ウィンドウがすべて隠れてしまうようにすることができます。親ウィンドウを持たないウィンドウ、 すなわち親ウィンドウがデスクトップ ウィンドウであるウィンドウは、 「トップ レベル ウィンドウ」と呼ばれます。トップ レベル ウィンドウの各ハンドルを取得するには、 EnumWindows関数を使います。EnumWindowsは、 取得したトップ レベル ウィンドウのハンドルを、 さらにアプリケーション定義のコールバック関数 (Windowsから呼び出される関数) に渡します。

ウィンドウは、 もう1つのウィンドウを所有したり、 または、 もう1つのウィンドウに所有させたりすることができます。「所有されているウィンドウ」は常に「オーナー ウィンドウ」の手前に表示され、 オーナー ウィンドウがアイコン化されるときは非表示にされます。オーナー ウィンドウが破棄されるときは、 所有されているウィンドウも破棄されます。

 

位置、 サイズ、 Z順序 (配置順序)

すべてのウィンドウは、 位置、 サイズ、 およびZ順序 (配置順序) を持ちます。位置とは、 画面上の左上隅からの相対座標によるウィンドウの左上隅の座標のことです。子ウィンドウの場合は、 親ウィンドウのクライアント領域からの相対座標になります。ウィンドウのサイズとは、 ピクセル単位でのウィンドウの幅および高さのことをいいます。ウィンドウの「Z順序 (配置順序)」とは、 ウィンドウが互いに重なり合っている場合の重なり順序のことです。

 

子ウィンドウIDまたはメニュー ハンドル

子ウィンドウには、 「子ウィンドウID」を持たせることができます。子ウィンドウIDとは、 子ウィンドウに関連付けられるアプリケーション定義の一意な値のことです。子ウィンドウIDはアプリケーションが複数の子ウィンドウを作成する場合に特に便利です。子ウィンドウを作成するとき、 アプリケーションは子ウィンドウIDを指定します。ウィンドウを作成した後、 アプリケーションはSetWindowLong関数を使ってIDを変更したり、 GetWindowLongを使ってIDを取得したりできます。

子ウィンドウ以外のウィンドウには、 すべてメニューを持たせることができます。アプリケーションは、 ウィンドウ クラスの登録時またはウィンドウの作成時にメニュー ハンドルを提供することにより、 メニューを持たせることができます。

 

インスタンス ハンドル

Win32ベースのアプリケーションは、 すべてアプリケーションに関連付けられているインスタンス ハンドルを持ちます。Windowsは、 アプリケーションの起動時にアプリケーションにインスタンス ハンドルを提供します。Windowsでは同じアプリケーションの複数のコピーを実行できるため、 Windowsは、 アプリケーションの個々のインスタンスを区別するために内部的にこのインスタンス ハンドルを使用します。アプリケーションは、 その中で使われる多くのさまざまなウィンドウ (ウィンドウを作成するウィンドウも含む) に対して、 インスタンス ハンドルを指定しなければなりません。

 

作成データ

すべてのウィンドウには、 アプリケーションに関連付けられるアプリケーション定義の作成データを持たせることができます。ウィンドウがはじめて作成されるとき、 Windowsは作成データを指すポインタを、 作成中のウィンドウのウィンドウ プロシージャに渡します。ウィンドウ プロシージャはこのデータを使ってアプリケーション定義の変数を初期化します。

 

メイン ウィンドウの作成

すべてのWin32ベースのアプリケーションは、 そのエントリ ポイントとしてWinMain関数を持っていなければなりません。WinMain関数は、 メイン ウィンドウのウィンドウ クラスの登録やメイン ウィンドウの作成などを含む、 数多くのタスクを実行します。WinMainは、 RegisterClass関数を呼び出してメイン ウィンドウ クラスを登録し、 CreateWindowEx関数を呼び出してメイン ウィンドウを作成します。

注:Microsoft(R) Windows NT(TM) では、 エントリ ポイントの名前にはWinMain以外の名前を指定できます。

Windowsは、 メイン ウィンドウを作成した後にそれを自動的に表示するわけではありません。アプリケーションはShowWindow関数を使ってメイン ウィンドウを表示させなければなりません。典型的には、 アプリケーションのWinMain関数の中から、 メイン ウィンドウの作成の直後にShowWindowを呼び出します。WinMainは2つのパラメータ、 すなわち、 メイン ウィンドウのハンドルと、 メイン ウィンドウをはじめて表示するときにそれをアイコン化または最大化して表示すべきかどうかを決めるフラグを、 ShowWindowに渡します。通常このフラグには、 Win32のヘッダー ファイルで定義されている、 SW_プリフィックスで始まる任意の定数をセットできます。しかし、 アプリケーションのメイン ウィンドウを表示させるためにShowWindowが呼び出されるときには、 SW_SHOWDEFAULTをセットしなければなりません。このフラグは、 アプリケーションを起動したプログラムによる指示のとおりにウィンドウを表示するよう、 Windowsに指示します。

 

ウィンドウ作成メッセージ

ウィンドウを作成するとき、 Windowsはそのウィンドウ用のウィンドウ プロシージャにメッセージを送ります。Windowsは、 ウィンドウの非クライアント領域が作成された後にWM_NCCREATEメッセージを送り、 クライアント領域が作成された後にWM_CREATEメッセージを送ります。ウィンドウ プロシージャは、 Windowsがウィンドウを表示する前にこれらのメッセージを受け取ります。いずれのメッセージも、 CREATESTRUCT構造体を指すポインタを持っています。この構造体には、 CreateWindowEx関数の中で指定された情報がすべて格納されています。通常、 ウィンドウ プロシージャは、 これらのメッセージを受け取った直後に初期化作業を実行します。

子ウィンドウを作成するときには、 WindowsはWM_NCCREATEメッセージとWM_CREATEメッセージを親ウィンドウに送った後に、 WM_PARENTNOTIFYメッセージを送ります。また、 ウィンドウの作成中にほかのメッセージも送ります。これらのメッセージの送られる数とその順序は、 ウィンドウ クラスとスタイル、 およびウィンドウの作成に使われた関数により異なります。各メッセージについて詳しくは、 それぞれの説明を参照してください。

 

マルチスレッド アプリケーション

Win32 ベースのアプリケーションは複数の実行スレッドを持つことができ、 各スレッドがウィンドウを作成できます。アプリケーションはEnumThreadWindows関数を使って、 特定のスレッドが作成したウィンドウを列挙させることができます。この関数は、 各スレッド ウィンドウのハンドルを、 さらにアプリケーション定義のコールバック関数に渡します。GetWindowThreadProcessId関数は、 特定のウィンドウを作成したスレッドのIDを返します。

 

ウィンドウ ハンドル

ウィンドウを作成した後、 作成関数は、 ウィンドウを一意に識別する「ウィンドウ ハンドル」を返します。アプリケーションは、 ウィンドウに対する動作を指示する関数の中で、 このウィンドウ ハンドルを使います。ウィンドウ ハンドルはHWNDデータ型を持っています。アプリケーションは、 ウィンドウ ハンドルを保持する変数を宣言するときに、 この型を使わなければなりません。

Win32 APIでは、 ある特定の関数でウィンドウ ハンドルとして代用できるいくつかの特殊な定数が定義されています。これらの定数はHWND_プリフィックスで始まります。たとえば、 アプリケーションはSetWindowPos関数の中でHWND_TOPまたはHWND_BOTTOMという定数を使い、 ウィンドウのZ順序をいちばん手前またはいちばん奥に移動させることができます。

NULL定数はウィンドウ ハンドルではありませんが、 アプリケーションは、 関数が作用するウィンドウを指定しない場合に、 この値を使うことができます。たとえば、 CreateWindowEx関数のhwndParentパラメータにNULLを指定すると、 親ウィンドウやオーナー ウィンドウを持たないウィンドウが作成されます。また、 ハンドルの代わりにNULLを返すことのある関数もあり、 この場合は指定された動作がどのウィンドウにも適用されないことを示します。

FindWindow関数を使えば、 指定されたクラス名またはウィンドウ名を持つウィンドウがシステム内に存在しているかどうかを調べることができます。そのようなウィンドウが存在する場合、 FindWindowはそのウィンドウのハンドルを返します。IsWindow関数は、 ウィンドウ ハンドルが、 既存の有効なウィンドウを識別するハンドルであるかどうかを判定します。

 

ウィンドウ スタイル

Win32 APIは、 汎用のウィンドウ スタイルとクラス固有のウィンドウ スタイルを提供しています。汎用のウィンドウ スタイルは、 WS_プリフィックスで始まる定数です。これらは組み合わせて指定することにより、 メイン ウィンドウやダイアログ ボックス、 子ウィンドウなど、 さまざまな種類のウィンドウを形成することができます。一方、 クラス固有のウィンドウ スタイルは、 エディット コントロールやリスト ボックスなどの定義済みのコントロール クラスに属するウィンドウの、 外観と動作を定義するものです。このトピックでは、 汎用のウィンドウ スタイルについて説明します。クラス特有の情報について詳しくは、 ボタンの概要、 リスト ボックスの概要、 エディット コントロールの概要、 コンボ ボックスの概要、 スクロール バーの概要、 およびスタティック コントロールの概要を参照してください。

通常は、 ウィンドウの作成時にウィンドウ スタイルを設定します。また、 SetWindowLong関数を使ってウィンドウの作成後にスタイルを設定することもできます。

 

オーバーラップ ウィンドウ

「オーバーラップ」ウィンドウとは、 タイトル バー、 境界、 およびクライアント領域を持つ、 トップ レベル ウィンドウのことです。このウィンドウはアプリケーションのメイン ウィンドウとして機能します。また、 オーバーラップ ウィンドウは、 コントロール メニュー、 アイコン化ボタン、 最大表示ボタン、 およびスクロール バーを持つこともできます。通常、 オーバーラップ ウィンドウはこれらすべての構成要素を含むメイン ウィンドウとして使われます。

オーバーラップ ウィンドウを作成するには、 CreateWindowEx関数の中でWS_OVERLAPPEDスタイルまたはWS_OVERLAPPEDWINDOWスタイルを指定します。WS_OVERLAPPEDスタイル付きで作成されたオーバーラップ ウィンドウには、 タイトル バーと境界が付きます。WS_OVERLAPPEDWINDOWスタイル付きで作成されたオーバーラップ ウィンドウには、 タイトル バー、 サイズ変更境界、 コントロール メニュー、 アイコン化ボタン、 および最大表示ボタンが付きます。

 

ポップアップ ウィンドウ

「ポップアップ ウィンドウ」とは、 オーバーラップ ウィンドウの特殊なもので、 通常はダイアログ ボックス、 メッセージ ボックスなど、 アプリケーションのメイン ウィンドウの外部に一時的に表示されるウィンドウとして使われます。ポップアップ ウィンドウではタイトル バーは省略可能です。省略しない場合、 ポップアップ ウィンドウは、 WS_OVERLAPPEDスタイル付きで作成されたオーバーラップ ウィンドウと同じになります。

ポップアップ ウィンドウを作成するには、 CreateWindowEx関数の中でWS_POPUPスタイルを指定します。タイトル バーを付けるには、 WS_CAPTIONスタイルも指定する必要があります。WS_POPUPWINDOWを使えば、 境界とコントロール メニューを持つポップアップウィンドウを作成できます。WS_POPUPWINDOWは、 コントロール メニューを表示させるために、 必ずWS_CAPTIONと組み合わせて指定してください。

 

子ウィンドウ

子ウィンドウは、 WS_CHILDスタイルを持ち、 必ず親ウィンドウのクライアント領域内に表示されます。通常は、 親ウィンドウのクライアント領域をいくつかの領域に分割するために、 子ウィンドウを使います。子ウィンドウを作成するには、 CreateWindowEx関数の中でWS_CHILDスタイルを指定します。

子ウィンドウは、 必ず親ウィンドウを持っていなければなりません。親ウィンドウになれるウィンドウは、 オーバーラップ ウィンドウ、 ポップアップ ウィンドウ、 または子ウィンドウです。親ウィンドウは、 CreateWindowEx関数を呼び出すときに指定します。CreateWindowEx関数の中でWS_CHILDスタイルを指定したにもかかわらず親ウィンドウを指定しない場合には、 そのウィンドウは作成されません。

子ウィンドウはクライアント領域を持ちますが、 それ以外の機能は特に要求しないかぎり持ちません。アプリケーションは子ウィンドウに対して、 タイトル バー、 コントロール メニュー、 アイコン化ボタン、 最大表示ボタン、 境界、 およびスクロール バーを要求できますが、 メニューを持たせることはできません。子ウィンドウのウィンドウ クラスの登録時、 または子ウィンドウの作成時のいずれかの時点でメニュー ハンドルを指定しても、 それは無視されます。

 

位置決め

Windowsは、 子ウィンドウの位置を決めるときに、 常に親ウィンドウのクライアント領域の左上隅からの相対座標を使います。親ウィンドウの境界の外には、 子ウィンドウは表示されません。親ウィンドウよりもサイズの大きい子ウィンドウを作成したり、 親ウィンドウの境界からその一部または全部がはみ出すように子ウィンドウの位置を設定したりした場合、 Windowsは子ウィンドウをクリップします。つまり、 親ウィンドウのクライアント領域の外側部分は表示されません。親ウィンドウに作用する動作は、 次の表に示すように、 子ウィンドウにも作用します。

親ウィンドウ 子ウィンドウ
破棄されるとき 親ウィンドウが破棄される前に破棄される。
非表示にされるとき 親ウィンドウが非表示にされる前に非表示にされる。子ウィンドウは、 親ウィンドウが可視のとき (表示されているとき) だけ、 可視である (表示される)。
移動されるとき 親ウィンドウのクライアント領域内で移動される。移動後のクライアント領域の描画は子ウィンドウが行う。
表示されるとき 親ウィンドウが表示された後に表示される。

 

クリッピング

Windowsは、 親ウィンドウのクライアント領域から子ウィンドウを自動的にクリップするわけではありません。つまり、 子ウィンドウと同じ位置の親ウィンドウの、 部分に何らかの描画操作を実行した場合は、 子ウィンドウの上に描画します。しかし、 親ウィンドウがWS_CLIPCHILDRENスタイルを持っている場合には、 親ウィンドウのクライアント領域から子ウィンドウをクリップします。子ウィンドウがクリップされると、 親ウィンドウはその上に描画できなくなります。

子ウィンドウは、 同じクライアント領域内でほかの子ウィンドウの上にオーバーラップさせることができます。1つまたは複数のほかの子ウィンドウとともに同じ親ウィンドウを共有している子ウィンドウは、 「兄弟ウィンドウ」と呼ばれます。兄弟ウィンドウは、 それらのうちの1つがWS_CLIPSIBLINGSスタイルを持っていないかぎり、 互いのクライアント領域内で描画を行うことができます。子ウィンドウに対してこのスタイルを指定した場合は、 その子ウィンドウとほかの兄弟ウィンドウとが重なる部分がクリップされます。

ウィンドウがWS_CLIPCHILDRENまたはWS_CLIPSIBLINGSのどちらかのスタイルを持っている場合は、 若干の実行性能の低下が起こります。子ウィンドウは各ウィンドウごとにシステム リソースを占有するため、 アプリケーションでは不必要に子ウィンドウを使わないようにしてください。最適な実行性能を得るため、 メイン ウィンドウを論理的に分割する必要のあるアプリケーションは、 その操作を子ウィンドウを使って行わずに、 メイン ウィンドウのウィンドウ プロシージャで行うようにしてください。

 

親ウィンドウとの親子関係

アプリケーションは、 SetParent関数を呼び出すことにより、 既存の子ウィンドウの親ウィンドウを変更できます。このとき、 Windowsは、 以前の親ウィンドウのクライアント領域からその子ウィンドウを削除し、 新しい親ウィンドウのクライアント領域に移動させます。SetParentでNULLハンドルを指定した場合は、 デスクトップ ウィンドウが新しい親ウィンドウになります。この場合には、 子ウィンドウがデスクトップ上に描画され、 デスクトップ上にあるほかのウィンドウの境界の外側に描画されます。GetParent関数は、 子ウィンドウの親ウィンドウのハンドルを取得します。

親ウィンドウは、 自分のクライアント領域部分を子ウィンドウに委ね、 子ウィンドウはこの領域からすべての入力を受け取るようになります。ウィンドウ クラスは、 親ウィンドウのそれぞれの子ウィンドウについてすべて同じにする必要はありません。つまり、 アプリケーションは、 親ウィンドウの中に外観や動作の異なる複数の子ウィンドウを表示させることができるわけです。たとえば、 ダイアログ ボックスには多くの種類のコントロールを含めることができますが、 各コントロールはユーザーからさまざまな種類のデータを受け取ることのできる子ウィンドウです。

子ウィンドウは1つの親ウィンドウしか持つことができませんが、 親ウィンドウは子ウィンドウをいくつでも持つことができ、 それぞれの子ウィンドウがさらに子ウィンドウ (孫ウィンドウ) を持つことができます。このようにして連結されたウィンドウは、 元の親ウィンドウの「子孫ウィンドウ」と呼ばれます。アプリケーションはIsChild関数を使い、 あるウィンドウが指定された親ウィンドウの子ウィンドウであるかまたは子孫ウィンドウであるかを調べることができます。

EnumChildWindows関数は、 親ウィンドウの子ウィンドウを列挙します。EnumChildWindowsは、 各子ウィンドウのハンドルをアプリケーション定義のコールバック関数に渡します。指定された親ウィンドウの子孫ウィンドウもまた列挙されます。

 

メッセージ

Windowsは、 子ウィンドウの入力メッセージをその子ウィンドウに直接渡します。このため、 親ウィンドウにはメッセージが渡されません。ただし、 子ウィンドウがEnableWindow関数によって使用不能にされている場合は例外です。この場合、 Windowsは、 子ウィンドウに渡されるはずだったすべての入力メッセージを親ウィンドウに代わりに渡します。これにより、 親ウィンドウは入力メッセージを調べて、 必要に応じて子ウィンドウを使用可能にすることが可能になります。

子ウィンドウは一意な整数IDを持つことができます。子ウィンドウIDは、 コントロール ウィンドウに対して作業を行うときに重要になります。アプリケーションはコントロールにメッセージを送ることによってその動作を指示しますが、 このときにコントロールの子ウィンドウIDを使ってメッセージを直接送ります。また、 コントロールはその親ウィンドウに通知メッセージを送りますが、 通知メッセージにはコントロールの子ウィンドウIDが含まれており、 親ウィンドウはこれを使ってメッセージを送ったコントロールを識別します。アプリケーションはほかの種類の子ウィンドウに対して、 CreateWindowEx関数のhmenuパラメータにメニュー ハンドルではなく子ウィンドウのID値を設定します。

 

ウィンドウの境界

Win32 APIは、 次の境界スタイルを提供します。
スタイル 説明
WS_BORDER 細い線の境界を持つウィンドウを作成します。
WS_DLGFRAME 二重の境界を持つウィンドウを作成します。通常、 このスタイルはダイアログ ボックスに対して使われます。このスタイルを持つウィンドウにはタイトル バーを付けることはできません。
WS_EX_DLGMODALFRAME 二重の境界を持つウィンドウを作成します。WS_DLGFRAMEスタイルとは異なり、 WS_CAPTIONスタイルを同時に指定してウィンドウにタイトル バーを付けることができます。
WS_THICKFRAME サイズ変更境界を持つウィンドウを作成します。

WS_OVERLAPPEDスタイルまたはWS_POPUPWINDOWスタイルを持つウィンドウは、 デフォルトでWS_BORDERスタイルが付きます。ほかの境界スタイルは、 オーバーラップ ウィンドウに種々の境界スタイルを付けるために、 いずれも必ずWS_OVERLAPPEDスタイルまたはWS_POPUPWINDOWスタイルと組み合わせて使います。

WS_POPUPスタイルまたはWS_CHILDスタイルを持つウィンドウに境界スタイルを1つも指定しない場合は、 境界を持たないウィンドウが作成されます。境界を持たない子ウィンドウは、 親ウィンドウのクライアント領域を分割するときにその分割線をユーザーに見せないようにする場合に使うことができます。

 

非クライアント領域の構成要素

ウィンドウの非クライアント領域には、 タイトル バー、 コントロール メニュー、 アイコン化ボタン、 最大表示ボタン、 サイズ変更境界、 水平スクロール バー、 および垂直スクロール バーを含めることができます。これらの構成要素を1つまたは複数持つウィンドウを作成するには、 CreateWindowEx関数の中で次のスタイルを指定します。

スタイル 説明
WS_CAPTION タイトル バーを持つウィンドウを作成します (WS_BORDERスタイルが付きます)。
WS_HSCROLL 水平スクロール バーを持つウィンドウを作成します。
WS_MAXIMIZEBOX 最大表示ボタンを持つウィンドウを作成します。
WS_MINIMIZEBOX アイコン化ボタンを持つウィンドウを作成します。
WS_SYSMENU タイトル バーの中にコントロール メニュー ボックスを持つウィンドウを作成します。必ずWS_CAPTIONスタイルを付けて指定します。
WS_VSCROLL 垂直スクロール バーを持つウィンドウを作成します。

 

初期状態

次のスタイルは、 作成されるウィンドウが使用可能または使用不能、 可視 (表示) または不可視 (非表示)、 アイコン表示または最大表示の、 どれになるかを決めます。

 

スタイル

説明

WS_DISABLED

初期状態で使用不能のウィンドウを作成します。使用不能のウィンドウは、 ユーザーからの入力を受け取ることができません。

WS_MAXIMIZE

初期状態で最大表示のウィンドウを作成します。

WS_MINIMIZE

初期状態でアイコン表示のウィンドウを作成します。

WS_VISIBLE

初期状態で可視 (表示) 状態のウィンドウを作成します。

 

親ウィンドウおよび子ウィンドウのスタイル

次のスタイルは、 親ウィンドウとその子ウィンドウ、 および子ウィンドウとその兄弟ウィンドウとのクリッピングの関係に影響します。

スタイル 説明
WS_CLIPCHILDREN 親ウィンドウの内部を描画するときに、 子ウィンドウが占める領域を除外します。親ウィンドウを作成するときは、 このスタイルを使います。
WS_CLIPSIBLINGS 互いに関連する子ウィンドウをクリップします。つまり、 ある子ウィンドウがWM_PAINTメッセージを受け取ると、 オーバーラップしているほかのすべての子ウィンドウはその子ウィンドウの領域からクリップされ、 子ウィンドウは更新されます。WS_CLIPSIBLINGSを指定しない場合、 子ウィンドウがオーバーラップしていると、 ある子ウィンドウのクライアント領域の内部を描画するときに、 その子ウィンドウと隣り合うほかの子ウィンドウのクライアント領域の内部を描画することが可能になります。

 

ダイアログ ボックスのスタイル

ダイアログ ボックスには、 方向キーとTabキーを処理する組み込みのキーボード インターフェイスが含まれています。ユーザーは、 マウスの代わりにこれらのキーを使って、 ダイアログ ボックス内のコントロールを操作できます。次のスタイルは、 組み込みキーボード インターフェイスによる方向キーおよびTabキーの処理方法に影響します。

スタイル 説明
WS_GROUP あるコントロール グループの中の最初のコントロールを指定します。ユーザーは、 方向キーを使ってグループ内のあるコントロールから次のコントロールへと、 キーボード フォーカスを変更することができます。最初のコントロールの後にあるWS_GROUPスタイルで定義されたコントロールは、 すべて同じグループに属します。グループはWS_GROUPスタイルを持つ次のコントロールで終わり、 同時にそのコントロールから次のグループが始まります。
WS_TABSTOP ユーザーがTabキーを押したときにキーボード フォーカスを受け取ることのできるコントロールを指定します。Tabキーを押すことにより、 キーボード フォーカスはWS_TABSTOPスタイルを持つ次のコントロールに移ります。

 

拡張スタイル

次のスタイルは、 CreateWindowEx関数のdwExStyleパラメータの中で指定することができます。

スタイル 説明

WS_EX_ACCEPTFILES

このスタイルで作成されたウィンドウはドラッグ アンド ドロップ ファイルを受け入れることを指定します。

WS_EX_DLGMODALFRAME

二重の境界を持つウィンドウを作成します。WS_DLGFRAMEスタイルとは異なり、 WS_CAPTIONスタイルを同時に指定してウィンドウにタイトル バーを付けることができます。

WS_EX_NOPARENTNOTIFY

このスタイルで作成された子ウィンドウは、 それが作成または破棄されるときに、 親ウィンドウにWM_PARENTNOTIFYメッセージを送らないことを指定します。

WS_EX_TOPMOST

このスタイルで作成されたウィンドウは、 ほかの最前面でないすべてのウィンドウよりも手前に表示され、 非アクティブ化されたときもその状態を保つことを指定します。

 

所有されているウィンドウ

オーバーラップ ウィンドウまたはポップアップ ウィンドウは、 ほかのオーバーラップ ウィンドウまたはポップアップ ウィンドウから所有されることができます。所有されているウィンドウには、 次のような制約があります。

  • 所有されているウィンドウは、 常にオーナー ウィンドウよりも手前に表示される。
  • Windowsは、 オーナー ウィンドウが破棄されるときに、 所有されているウィンドウを自動的に破棄する。
  • オーナー ウィンドウがアイコン化されているとき、 所有されているウィンドウは表示されない。
オーナー ウィンドウになれるのは、 オーバーラップ ウィンドウとポップアップ ウィンドウだけです。子ウィンドウはオーナー ウィンドウにはなれません。アプリケーションは、 WS_OVERLAPPEDスタイルまたはWS_POPUPスタイルを付けてウィンドウを作成するときに、 CreateWindowEx関数のhwndParentパラメータとしてオーナーのウィンドウ ハンドルを指定することにより、 所有されるウィンドウを作成できます。hwndParentパラメータには、 オーバーラップ ウィンドウまたはポップアップ ウィンドウを識別しなければなりません。hwndParentパラメータが子ウィンドウを識別した場合は、 Windowsはその子ウィンドウのトップ レベルの親ウィンドウに、 所有権を割り当てます。所有されているウィンドウを作成すると、 アプリケーションはそのウィンドウの所有権をほかのウィンドウに移すことができなくなります。

ダイアログ ボックスおよびメッセージ ボックスは、 デフォルトで所有されているウィンドウになります。アプリケーションは、 ダイアログ ボックスやメッセージ ボックスを作成する関数を呼び出すときに、 そのオーナー ウィンドウを指定します。

GW_OWNERフラグを指定してGetWindow関数を使えば、 ウィンドウのオーナーのハンドルを取得できます。

 

使用不能のウィンドウ

ウィンドウは使用不能にすることができます。「使用不能のウィンドウ」は、 キーボードやマウスからの入力を受け取りません。しかし、 ほかのウィンドウやほかのアプリケーション、 およびWindowsから送られるメッセージは、 受け取ることができます。通常、 アプリケーションは、 ユーザーにウィンドウを使わせないようにするためにウィンドウを使用不能にします。たとえば、 ダイアログ ボックス内のプッシュ ボタンを使用不能にすれば、 ユーザーはそのボタンを選ぶことができなくなります。使用不能のウィンドウはいつでも使用可能に戻すことができ、 再び通常の入力を受け取るようにすることができます。

デフォルトでは、 ウィンドウは使用可能として作成されます。しかし、 アプリケーションはWS_DISABLEDスタイルを指定して、 新しいウィンドウを使用不能の状態で作成することができます。また、 EnableWindow関数を使えば、 既存のウィンドウの使用可能または使用不能の状態を切り替えることができます。Windowsは、 ウィンドウの使用可能状態が変更されようとしているときに、 そのウィンドウにWM_ENABLEメッセージを送ります。ウィンドウが使用可能かどうかは、 IsWindowEnabled関数を使って判断できます。

子ウィンドウが使用不能にされると、 Windowsはその子ウィンドウのマウス入力メッセージを親ウィンドウに送ります。親ウィンドウはこのメッセージを使って、 子ウィンドウを使用可能にするかどうかを決めます。

キーボード入力を受け取ることのできるウィンドウは、 一度に1つだけです。キーボード入力を受け取ることのできるウィンドウは、 キーボード フォーカスを持つ、 といわれます。キーボード フォーカスを持つウィンドウをEnableWindow関数を使って使用不能にした場合、 ウィンドウは使用不能になるばかりでなく、 キーボード フォーカスをも失います。そして、 EnableWindowはキーボード フォーカスをNULLに設定し、 フォーカスを持つウィンドウがないことを示します。子ウィンドウやほかの子孫ウィンドウがキーボード フォーカスを持っている場合は、 その親ウィンドウが使用不能にされたときに、 その子孫ウィンドウはフォーカスを失います。キーボード フォーカスについて詳しくは、 キーボード入力の概要を参照してください。

 

前景ウィンドウおよび背景ウィンドウ

プロセスはそれぞれ複数の実行スレッドを持つことができ、 それぞれのスレッドは複数のウィンドウを作成できます。ユーザーが現在作業をしているウィンドウを作成したスレッドはフォアグラウンド スレッドと呼ばれ、 そのウィンドウは「前景ウィンドウ」と呼ばれます。また、 これ以外のスレッドはバックグラウンド スレッドと呼ばれ、 それらのスレッドが作成したウィンドウは「背景ウィンドウ」と呼ばれます。

各スレッドは、 自分が占有するCPU時間の量を決定する優先順位レベルを持っています。スレッドの優先順位はアプリケーションが自分で設定することもできますが、 通常はフォアグラウンド スレッドがバックグラウンド スレッドよりもわずかに高い優先順位レベルを持ちます。このため、 フォアグラウンド スレッドはバックグラウンド スレッドよりも多くのCPU時間を占有します。フォアグラウンド スレッドは、 標準の基本優先順位として優先順位9を持ちます。一方、 バックグラウンド スレッドは、 標準の基本優先順位として優先順位7を持ちます。

ユーザーは、 ウィンドウをクリックするか、 またはAlt+TabキーかAlt+Escキーの組み合わせを使うことにより、 前景ウィンドウを設定します。アプリケーションからは、 SetForegroundWindow関数を使って前景ウィンドウを設定します。新しくフォアグラウンドとして設定されたウィンドウがトップ レベル ウィンドウの場合、 Windowsはそれをアクティブ化します。トップ レベル ウィンドウでない場合は、 そのウィンドウに関連付けられているトップ レベル ウィンドウをアクティブ化します。前景ウィンドウのハンドルを取得するには、 GetForegroundWindow関数を使います。

 

表示状態

ウィンドウは、 いつでもアクティブまたは非アクティブにされたり、 表示されたり非表示にされたりします。また、 いつでもアイコン表示されたり、 最大表示されたり、 元のサイズで表示されたりします。これらのウィンドウの特徴を総称して、 ウィンドウの「表示状態」と呼びます。

 

アクティブ ウィンドウ

「アクティブ ウィンドウ」とは、 ユーザーが現在作業をしているアプリケーションのトップ レベル ウィンドウのことです。アクティブ ウィンドウであることをユーザーが容易に識別できるようにするため、 WindowsはそのウィンドウをZ順序のいちばん手前に表示させ、 ウィンドウのタイトル バーと境界をシステム定義のアクティブ ウィンドウの色に変更します。アクティブ ウィンドウにできるのはトップ レベル ウィンドウだけです。ユーザーが子ウィンドウで作業をしているときには、 その子ウィンドウのトップ レベルの親ウィンドウをアクティブ化します。

ある時点においてシステム内でアクティブなトップ レベル ウィンドウは1つだけです。ユーザーはトップ レベル ウィンドウ (またはその子ウィンドウの1つ) をクリックするか、 またはAlt+EscキーかAlt+Tabキーの組み合わせを使うことにより、 ウィンドウをアクティブ化します。アプリケーションからは、 SetActiveWindow関数を呼び出してトップ レベル ウィンドウをアクティブ化します。この関数のほか、 SetWindowPosやDeferWindowPos、 SetWindowPlacement、 DestroyWindowなどの多くの関数により、 種々のトップ レベル ウィンドウをWindowsにアクティブ化させることができます。アプリケーションはさまざまなトップ レベル ウィンドウをいつでもアクティブ化できますが、 ユーザーが混乱しないように、 アクティブ化はユーザーへの応答をするときだけ行うようにしてください。アクティブ ウィンドウのハンドルを取得するには、 GetActiveWindow関数を使います。

あるアプリケーションのトップ レベル ウィンドウから別のアプリケーションのトップ レベル ウィンドウにアクティブ ウィンドウが移ると、 Windowsは両方のアプリケーションにそのことを通知するWM_ACTIVATEAPPメッセージを送ります。同じアプリケーション内で異なるトップ レベル ウィンドウにアクティブ ウィンドウが移ったときは、 両方のウィンドウにWM_ACTIVEメッセージが送られます。

 

可視性

ウィンドウは、 表示させたり (可視にしたり) 表示させなかったり (不可視にしたり) できます。Windowsは「可視ウィンドウ」を画面に表示します。「不可視ウィンドウ」は描画しないことにより画面に表示しません。ウィンドウが可視の場合、 ユーザーはそのウィンドウに入力して、 ウィンドウの出力を見ることができます。ウィンドウが不可視の場合には、 効果的には使用不能な状態になります。不可視ウィンドウは、 Windowsやほかのウィンドウからのメッセージを処理することはできますが、 ユーザーからの入力を処理することはできず、 出力の表示も処理できません。アプリケーションはウィンドウの作成時にその可視性を設定します。また、 作成後に可視状態を変更することもできます。

ウィンドウは、 WS_VISIBLEスタイルが設定されているときに可視になります。デフォルトでは、 CreateWindowEx関数はWS_VISIBLEスタイルを指定しないかぎり不可視ウィンドウを作成します。通常、 アプリケーションは、 ウィンドウの作成過程をユーザーに見せないようにするために、 作成後にWS_VISIBLEスタイルを設定します。たとえば、 ウィンドウの外観をカスタマイズする間、 アプリケーションは新しいウィンドウを非表示状態にしておく場合があります。CreateWindowEx関数の中でWS_VISIBLEスタイルが指定されると、 Windowsは、 ウィンドウが作成された後にそのウィンドウにWM_SHOWWINDOWメッセージを送ります。しかし、 表示する前にはメッセージを送りません。

アプリケーションは、 IsWindowVisible関数を使ってウィンドウが可視であるかどうかを判断することができます。ShowWindow、 SetWindowPos、 DeferWindowPos、 またはSetWindowPlacementの各関数を使えば、 ウィンドウを表示させたり (可視にしたり)、 または非表示にしたりできます。これらの関数は、 ウィンドウに対してWS_VISIBLEスタイルを設定したり、 または設定を削除することによって、 ウィンドウを表示させたり非表示にしたりします。また、 表示および非表示を行う前にWM_SHOWWINDOWメッセージをウィンドウに送ります。

オーナー ウィンドウがアイコン化されると、 Windowsはそのウィンドウに所有されているウィンドウを自動的に非表示にします。同様に、 オーナー ウィンドウが元の表示に戻されると、 Windowsはそのウィンドウに所有されているウィンドウを自動的に表示します。いずれの場合も、 Windowsは、 ウィンドウの表示および非表示を行う前に、 所有されているウィンドウにWM_SHOWWINDOWメッセージを送ります。また、 アプリケーションは、 所有されているウィンドウをアイコン化せずに非表示にしたり、 そのオーナーを非表示にしたりしなければならない場合がしばしばあります。このような場合は、 ShowOwnedPopups関数を使います。この関数は、 所有されているすべてのウィンドウのWS_VISIBLEスタイルを設定したり、 または設定を削除します。そして、 ウィンドウの表示および非表示を行う前に、 所有されているすべてのウィンドウにWM_SHOWWINDOWメッセージを送ります。オーナー ウィンドウを非表示にしても、 所有されているウィンドウの可視状態は変わりません。

親ウィンドウが可視になると、 その子ウィンドウもまた可視になります。同様に、 親ウィンドウが不可視になると、 その子ウィンドウもまた不可視になります。しかし、 親ウィンドウがアイコン化されても子ウィンドウの可視状態は変わりません。つまり、 子ウィンドは親ウィンドウといっしょにアイコン化されますが、 WS_VISIBLEスタイルは変わらないということです。

ウィンドウがWS_VISIBLEスタイルを持っていても、 ユーザーはそのウィンドウを画面上で見ることができない場合があります。たとえば、 ほかのウィンドウがそのウィンドウの上に完全にオーバーラップしていたり、 画面の端よりも外に出ていたりする場合があります。また、 可視の子ウィンドウも、 親子関係に基づいて確立されているクリッピングの規則の影響を受けます。親ウィンドウが可視でない場合は、 その子ウィンドウもまた可視ではなくなります。子ウィンドウは親ウィンドウの左上隅から相対的に描画されるため、 親ウィンドウが画面の端よりも外に出ていると、 子ウィンドウも画面の外に出されてしまいます。たとえば、 子ウィンドウが含まれている親ウィンドウをユーザーが画面の端いっぱいに移動させてしまうと、 それらのウィンドウが両方ともWS_VISIBLEスタイルを持っていても、 その子ウィンドウを見ることができなくなる場合があります。

 

アイコン化ウィンドウ、 最大表示ウィンドウ、 または復元ウィンドウ

「最大表示ウィンドウ」とは、 WS_MAXIMIZEDスタイルを持つウィンドウのことです。デフォルトでは、 Windowsはウィンドウが画面全体に表示されるように最大表示ウィンドウを拡大します。子ウィンドウの場合には、 親ウィンドウのクライアント領域全体に表示されるように拡大します。ウィンドウのサイズは最大表示ウィンドウと同じサイズに設定することもできますが、 最大表示ウィンドウはそれとは多少異なります。Windowsは、 ウィンドウのタイトル バーを、 画面のいちばん上、 または親ウィンドウのクライアント領域のいちばん上に自動的に移動させます。また、 ウィンドウのサイズ変更境界の機能と、 タイトル バーによるウィンドウの位置変更の機能を使用不能にします (このため、 ユーザーはタイトル バーをドラッグしてウィンドウを動かすことができなくなります)。

「アイコン化ウィンドウ」とは、 WS_MINIMIZEDスタイルを持つウィンドウのことです。デフォルトでは、 Windowsはウィンドウをアイコンのサイズにまで縮小し、 アイコン化されたウィンドウを、 画面の下部、 または親ウィンドウのクライアント領域の下部に移動させます。画面やクライアント領域の下部は、 しばしば「アイコン領域」と呼ばれることがあります。Windowsは、 アプリケーションが特に位置を指定しないかぎり、 アイコン領域内で最初に利用できる位置にアイコン化ウィンドウを移動させます。「復元ウィンドウ」とは、 そのサイズと位置が以前のアイコンまたは最大表示の状態に戻されているウィンドウのことです。

アプリケーションがCreateWindowEx関数の中でWS_MAXIMIZEDスタイルまたはWS_MINIMIZEDスタイルを指定した場合、 作成されるウィンドウは初期状態でアイコン化または最大化されて表示されます。ウィンドウの作成後、 アプリケーションはCloseWindow関数を使ってウィンドウをアイコン化することができます。ArrangeIconicWindows関数は、 アイコン化されたアプリケーションのトップ レベル ウィンドウを、 画面の下部内に整列させます。または、 親ウィンドウ内のアイコン化された子ウィンドウを、 親ウィンドウの下部内に整列させます。

ShowWindow関数は、 ウィンドウをアイコン化、 最大化、 または復元します。また同時に、 ウィンドウの可視状態とアクティブ状態を設定することもできます。SetWindowPlacement関数はShowWindowと同じ機能を持っていますが、 そのほかに、 ウィンドウのデフォルトのアイコン化位置、 最大化位置、 および復元位置を、 それぞれ変更することができます。

IsZoomed関数とIsIconic関数は、 それぞれ指定されたウィンドウが最大化されているかどうか、 またはアイコン化されているかどうかを調べます。GetWindowPlacement関数は、 ウィンドウのアイコン化位置、 最大化位置、 および復元位置をそれぞれ取得し、 ウィンドウの表示状態も取得します。

アイコン化ウィンドウを最大化または復元するコマンドを受け取ると、 WindowsはそのウィンドウにWM_QUERYOPENメッセージを送ります。ウィンドウ プロシージャがFALSEを返した場合は、 Windowsは最大化および復元のコマンドを無視します。

Windowsは、 最大表示ウィンドウのサイズと位置を、 最大表示ウィンドウに対するシステム定義のデフォルト値に自動的に設定します。アプリケーションは、 SetWindowPlacement関数を使うか、 またはWM_GETMINMAXINFOメッセージを処理することで、 これらのデフォルト値を変更することができます。WM_GETMINMAXINFOメッセージは、 Windowsがウィンドウを最大化しようとするときにそのウィンドウに送られるメッセージです。このメッセージにはMINMAXINFO構造体を指すポインタが含まれています。この構造体には、 Windowsがウィンドウの最大化時のサイズと位置を設定するときに使う値が格納されています。これらの値を変えれば、 デフォルト値が変更されます。

 

ウィンドウのサイズと位置

ウィンドウのサイズと位置は境界長方形として表現され、 その座標は画面または親ウィンドウからの相対座標で指定されます。トップ レベル ウィンドウの座標は、 画面の左上隅からの相対座標になります。また、 子ウィンドウの座標は、 親ウィンドウの左上隅からの相対座標になります。アプリケーションは、 ウィンドウの作成時にその初期状態でのサイズと位置を指定しますが、 それらはいつでも変更できます。境界長方形について詳しくは、 塗りつぶされた図形の概要を参照してください。

 

サイズ

ウィンドウのサイズ (幅および高さ) は、 ピクセル単位で指定されます。幅または高さが0のウィンドウを作成することもできます。アプリケーションがウィンドウの幅と高さを両方とも0に設定した場合は、 Windowsはそのサイズをデフォルトの最小ウィンドウ サイズに設定します。デフォルトの最小ウィンドウ サイズを取得するには、 SM_CXMINフラグとSM_CYMINフラグを指定してGetSystemMetrics関数を使います。

アプリケーションでは、 特定のサイズのクライアント領域を持つウィンドウを作成したい場合があります。AdjustWindowRect関数およびAdjustWindowRectEx関数は、 望ましいクライアント領域のサイズに基づいて、 必要なウィンドウのサイズを計算します。これらの関数が返したサイズは、 CreateWindowEx関数に渡すことができます。

アプリケーションは、 ウィンドウが極端に大きくなるようにサイズを変更することができますが、 画面のサイズよりも大きくならないようにしてください。ウィンドウのサイズを設定するときは、 その前にSM_CXSCREENフラグとSM_CYSCREENフラグを指定してGetSystemMetrics関数を呼び出し、 画面の幅と高さを調べておくようにしてください。

 

位置

ウィンドウの位置は、 その左上隅の座標として定義されます。この座標はしばしば「ウィンドウ座標」と呼ばれ、 常に画面の左上隅からの相対座標になります。ウィンドウが子ウィンドウの場合には、 その親ウィンドウのクライアント領域の左上隅からの相対座標になります。たとえば、 座標 (10, 10) を持つトップ レベル ウィンドウは、 画面の左上隅の位置から右に10ピクセル、 下に10ピクセルの位置に、 その左上隅が置かれます。また、 座標 (10, 10) を持つ子ウィンドウは、 その親ウィンドウのクライアント領域の左上隅の位置から右に10ピクセル、 下に10ピクセルの位置に、 その左上隅が置かれます。

WindowFromPoint関数は、 画面上の特定の点を占めているウィンドウのハンドルを取得します。ChildWindowFromPoint関数は、 親ウィンドウのクライアント領域内において特定の点を占めている子ウィンドウのハンドルを取得します。

 

デフォルトのサイズと位置

アプリケーションは、 CreateWindowEx関数の中でCW_USEDEFAULT定数を指定することにより、 トップ レベル ウィンドウの初期状態でのサイズと位置をWindowsに計算させることができます。アプリケーションがウィンドウの座標をCW_USEDEFAULTに設定し、 ほかにトップ レベル ウィンドウを作成しなかった場合は、 Windowsは、 新しく作成されるウィンドウの位置を画面の左上隅からの相対位置に設定します。ほかにトップ レベル ウィンドウを作成した場合には、 Windowsはウィンドウの位置を、 アプリケーションが直前に作成したばかりのトップ レベル ウィンドウからの相対位置に設定します。また、 同様に、 幅パラメータおよび高さパラメータがCW_USEDEFAULTに設定された場合は、 Windowsは新しいウィンドウのサイズを計算します。ほかにトップ レベル ウィンドウを作成した場合には、 Windowsはアプリケーションが直前に作成したばかりのトップ レベル ウィンドウのサイズを基に、 新しいウィンドウのサイズを計算します。子ウィンドウまたはポップアップ ウィンドウの作成時にCW_USEDEFAULTを指定すると、 Windowsはウィンドウのサイズをデフォルトの最小ウィンドウ サイズに設定します。

 

トラッキング サイズ

Windowsは、 WS_THICKFRAMEスタイルを持つウィンドウに対して、 最大および最小のトラッキング サイズを管理しています。このスタイルを持つウィンドウは、 サイズ変更境界を持ちます。「最小トラッキング サイズ」および「最大トラッキング サイズ」とは、 ユーザーがウィンドウのサイズ変更境界をドラッグすることにより生成できる、 最小および最大のウィンドウ サイズのことです。

ウィンドウの最小および最大のトラッキング サイズは、 ウィンドウの作成時にシステム定義のデフォルト値が設定されます。この値は、 WM_GETMINMAXINFOメッセージ処理の中で取得し、 変更することができます。このメッセージについて詳しくは、 サイズおよび位置を扱うメッセージを参照してください。

 

システム コマンド

コントロール メニュー付きのウィンドウを持つアプリケーションは、 システム コマンドを送ることによってそのサイズと位置を変更できます。システム コマンドは、 ユーザーがコントロール メニューからコマンドを選んだときに生成されます。アプリケーションは、 ウィンドウにWM_SYSCOMMANDメッセージを送ることにより、 このユーザーの操作をエミュレートすることができます。次のシステム コマンドは、 ウィンドウのサイズと位置に作用します。

コマンド 説明
SC_CLOSE ウィンドウをクローズします。このコマンドは、 クローズするウィンドウにWM_CLOSEメッセージを送ります。ウィンドウは、 後始末に必要な処理を実行して、 自分自身を破棄します。
SC_MAXIMIZE ウィンドウを最大化します。
SC_MINIMIZE ウィンドウをアイコン化します。
SC_RESTORE アイコン化または最大化されていたウィンドウを、 元のサイズと位置に戻します。
SC_SIZE サイズ変更コマンドを起動します。ユーザーは、 マウスやキーボードを使ってウィンドウのサイズを変更できます。

 

Z順序 (配置順序)

ウィンドウのZ順序 (配置順序) とは、 オーバーラップしているウィンドウのスタック内におけるウィンドウの重なり順序を示すものです。ウィンドウ スタックは、 画面上において仮想的なZ軸を考えたときに、 画面から手前に向かう方向を正方向とします。Z順序でいちばん手前にあるウィンドウは、 ほかのすべてのウィンドウよりも上に表示されます。また、 いちばん奥にあるウィンドウは、 ほかのすべてのウィンドウよりも下に表示されます。アプリケーションは、 指定されたウィンドウの後ろにウィンドウを置くか、 またはスタックのいちばん上かいちばん下に置くことにより、 ウィンドウのZ順序を設定します。

Windowsは、 トップ レベル ウィンドウ用、 兄弟ウィンドウ用、 および最前面 (topmost) ウィンドウ用の、 3種類のZ順序を個別に管理しています。「最前面ウィンドウ」とは、 それがアクティブであるかフォアグラウンドであるかにかかわらず、 最前面ウィンドウ以外のすべてのウィンドウよりも上に表示されるウィンドウのことです。最前面ウィンドウは、 WS_EX_TOPMOSTスタイルを持ちます。

デフォルトでは、 Windowsはウィンドウの作成時にウィンドウをいちばん手前に置きます。ユーザーは別のウィンドウをアクティブにすることでZ順序を変更し、 Windowsはアクティブ ウィンドウを常にいちばん手前に置きます。アプリケーションでウィンドウをいちばん手前に表示させるには、 BringWindowToTop関数を使います。いちばん手前のウィンドウは、 SetWindowPos関数またはDeferWindowPos関数を使ってZ順序を変更することができます。

 

サイズおよび位置を扱う関数

アプリケーションはウィンドウを作成した後、 MoveWindow、 SetWindowPos、 DeferWindowPos、 SetWindowPlacementなどのさまざまな関数を呼び出して、 ウィンドウのサイズや位置を設定することができます。MoveWindow関数およびSetWindowPos関数は、 いずれも単一のアプリケーション ウィンドウのサイズまたは位置を設定します。SetWindowPos関数は、 ウィンドウの表示状態に作用する1組のフラグを設定します。MoveWindowではこれらのフラグは設定できません。BeginDeferWindowPos、 DeferWindowPos、 およびEndDeferWindowPosの3つの関数は、 多数のウィンドウのサイズ、 位置、 Z順序、 および表示状態を同時に設定するために、 いっしょに使われます。SetWindowPlacement関数は、 1つのウィンドウのアイコン化位置、 最大化位置、 復元時のサイズと位置、 および表示状態を設定します。

GetWindowRect関数を使えば、 ウィンドウの境界長方形の座標を取得できます。GetWindowRectは、 ウィンドウの左上隅および右下隅の座標をRECT構造体に設定します。設定される座標は、 子ウィンドウの場合を含めて、 画面左上隅からの相対座標になります。ScreenToClient関数またはMapWindowPoints関数は、 子ウィンドウの境界長方形の画面座標を、 親ウィンドウのクライアント領域からの相対座標に変換します。

GetClientRect関数は、 ウィンドウのクライアント領域の座標を取得します。GetClientRectは、 クライアント領域の左上隅および右下隅の座標をRECT構造体に設定しますが、 座標はクライアント領域自身からの相対座標になります。つまり、 クライアント領域の左上隅の座標は常に (0, 0) になり、 右下隅の座標は、 クライアント領域の幅および高さになります。

 

サイズおよび位置を扱うメッセージ

Windowsは、 ウィンドウのサイズや位置が変更されようとするときに、 そのウィンドウにWM_GETMINMAXINFOメッセージを送ります。たとえば、 ユーザーがコントロール メニューから[移動]コマンドまたは[サイズ変更]コマンドを選んだとき、 サイズ変更境界やタイトル バーをクリックしたとき、 あるいはアプリケーションがSetWindowPos関数を呼び出してウィンドウの移動やサイズ変更をしようとしたときに、 WM_GETMINMAXINFOメッセージが送られます。WM_GETMINMAXINFOメッセージにはMINMAXINFO構造体を指すポインタが含まれています。この構造体には、 ウィンドウの最大化時のデフォルトのサイズと位置、 およびデフォルトの最小および最大のトラッキング サイズが格納されています。

アプリケーションは、 WM_GETMINMAXINFOメッセージを処理し、 MINMAXINFO構造体の対応するメンバを設定することにより、 これらのデフォルト値を変更できます。WM_GETMINMAXINFOメッセージを受け取るには、 ウィンドウがWS_THICKFRAMEスタイルまたはWS_CAPTIONスタイルを持っていなければなりません。WS_THICKFRAMEスタイルを持つウィンドウは、 その作成処理の間にこのメッセージを受け取り、 ウィンドウが移動またはサイズ変更されているときにも同様に受け取ります。

Windowsは、 ウィンドウのサイズ、 位置、 Z順序、 または表示状態が変更されようとしているときに、 そのウィンドウにWM_WINDOWPOSCHANGINGメッセージを送ります。このメッセージにはWINDOWPOS構造体を指すポインタが含まれています。この構造体には、 ウィンドウの新しいサイズ、 位置、 Z順序、 および表示状態を指定します。WINDOWPOS構造体の各メンバを設定すれば、 ウィンドウの新しいサイズ、 位置、 および外観を作用させることができます。

ウィンドウのサイズ、 位置、 Z順序、 および表示状態を変更した後に、 WindowsはWM_WINDOWPOSCHANGEDメッセージをウィンドウに送ります。このメッセージにはWINDOWPOS構造体を指すポインタが含まれています。この構造体は、 ウィンドウの新しいサイズ、 位置、 Z順序、 および表示状態をウィンドウに通知します。WM_WINDOWPOSCHANGEDメッセージで渡されたWINDOWPOS構造体の各メンバを設定しても、 ウィンドウには作用しません。WM_SIZEメッセージおよびWM_MOVEメッセージを処理しなければならないウィンドウは、 必ずWM_WINDOWPOSCHANGEDメッセージをDefWindowProc関数に渡さなければなりません。そうしない場合、 WindowsはWM_SIZEメッセージおよびWM_MOVEメッセージをウィンドウに送りません。

Windowsは、 ウィンドウの作成時またはサイズ変更時に、 WM_NCCALCSIZEメッセージをウィンドウに送ります。Windowsはこのメッセージを使って、 ウィンドウのクライアント領域のサイズ、 およびクライアント座標のウィンドウの左上隅からの相対位置を計算します。通常、 ウィンドウはこのメッセージをデフォルトのウィンドウ プロシージャに渡します。しかし、 アプリケーションでウィンドウの非クライアント領域をカスタマイズする場合や、 ウィンドウのサイズ変更時にクライアント領域部分を保存する場合には、 このメッセージを処理すると便利です。ウィンドウのサイズについて詳しくは、 ペイントと描画の概要を参照してください。

 

ウィンドウの破棄

一般に、 アプリケーションは自分が作成したウィンドウをすべて破棄しなければなりません。これには、 DestroyWindow関数を使います。ウィンドウが破棄されると、 システムはそのウィンドウが表示されていればそれを非表示にして、 ウィンドウに関連付けられている内部データをすべて削除します。これにより、 ウィンドウ ハンドルは無効になり、 アプリケーションで使うことができなくなります。

アプリケーションで作成するウィンドウの多くは、 作成されたすぐ後に破棄されます。たとえば、 通常のダイアログ ボックス ウィンドウは、 アプリケーションがユーザーから十分な入力情報を得て作業を実行できるようになった時点で、 直ちに破棄されます。最終的には、 アプリケーションのメイン ウィンドウが (アプリケーションの終了前に) 破棄されます。

ウィンドウを破棄するときは、 ウィンドウに関連付けられているデータをすべて保存するか、 または削除します。そして、 ウィンドウ用に割り当てられていたシステム リソースを解放します。アプリケーションが解放しなかったリソースは、 Windowsがそれらを解放します。

ウィンドウを破棄しても、 そのウィンドウが作成されたときのウィンドウ クラスには影響はありません。新しいウィンドウはそのクラスを使って依然として作成することができ、 そのクラスを持つ既存のウィンドウも引き続き操作できます。

ウィンドウを破棄すると、 そのウィンドウの子孫ウィンドウも破棄されます。DestroyWindow関数、 WM_DESTROYメッセージをまず破棄するウィンドウに送り、 続けてその子ウィンドウと子孫ウィンドウに送ります。このようにして、 破棄されているウィンドウのすべての子孫ウィンドウもまた破棄されます。

コントロール メニューを持つウィンドウは、 ユーザーがコントロール メニューの[閉じる]コマンドを選んだときに、 WM_CLOSEメッセージを受け取ります。このメッセージを処理することにより、 アプリケーションはウィンドウを破棄する前にユーザーに確認をとることができます。ユーザーがウィンドウを破棄してもよいと確定した場合は、 DestroyWindow関数を呼び出してウィンドウを破棄することができます。

破棄されているウィンドウがアクティブ ウィンドウである場合、 アクティブ状態とフォーカス状態の両方がほかのウィンドウに移ります。アクティブ ウィンドウになるウィンドウは、 Alt+Escキーの組み合わせにより次に選ばれたウィンドウになります。この後、 新しいアクティブ ウィンドウは、 どのウィンドウがキーボード フォーカスを受け取るかを決定します。

 

ウィンドウの使用

次のトピックからは、 アプリケーションでのウィンドウの作成方法と使用方法、 および以下に示す処理の実行方法を説明しています。

  • メイン ウィンドウの作成方法

  • 子ウィンドウの作成、 列挙、 およびサイズ変更の方法

  • ウィンドウを破棄する方法

 

メイン ウィンドウの作成方法

アプリケーションが最初に作成するウィンドウは、 通常はメイン ウィンドウです。メイン ウィンドウを作成するには、 CreateWindowEx関数を使い、 ウィンドウ クラス、 ウィンドウ名、 ウィンドウ スタイル、 サイズ、 位置、 メニュー ハンドル、 インスタンス ハンドル、 および作成データを指定します。メイン ウィンドはアプリケーション定義のウィンドウ クラスに属するため、 作成する前にウィンドウ クラスを登録して、 そのクラスのウィンドウ プロシージャを用意しなければなりません。

ほとんどのアプリケーションは、 WS_OVERLAPPEDWINDOWスタイルを使ってメイン ウィンドウを作成するのがふつうです。このスタイルにより、 ウィンドウにはタイトル バー、 コントロール メニュー、 サイズ変更境界、 アイコン化ボタン、 および最大表示ボタンが付けられます。CreateWindowEx関数は、 そのウィンドウを一意に識別するハンドルを返します。

次の例では、 アプリケーション定義のウィンドウ クラスに属するメイン ウィンドウを作成しています。この例では、 「メイン ウィンドウ」というウィンドウ名がタイトル バーに表示されます。WS_VSCROLLスタイルとWS_HSCROLLスタイルをWS_OVERLAPPEDWINDOWスタイルとくみ合わせることにより、 アプリケーションは、 WS_OVERLAPPEDWINDOWスタイルにより提供される構成要素のほかに、 水平および垂直のスクロール バーを持ったメイン ウィンドウを作成します。4箇所で使われているCW_USEDEFAULT定数は、 ウィンドウの初期状態でのサイズと位置をシステム定義のデフォルト値に設定します。メニュー ハンドルに指定されているNULLは、 ウィンドウ クラスに対して定義されているメニューをウィンドウが持つことを示します。

HINSTANCE hinst;
HWND hwndMain;

.
. /* Register the window class for the main window. */
.


/* Create the main window. */

hwndMain = CreateWindowEx(
    0,                      /* no extended styles          */
    "MainWClass",           /* class name                  */
    "Main Window",          /* window name                 */
    WS_OVERLAPPEDWINDOW |   /* overlapped window           */
        WS_HSCROLL |        /* horizontal scroll bar       */
        WS_VSCROLL,         /* vertical scroll bar         */
    CW_USEDEFAULT,          /* default horizontal position */
    CW_USEDEFAULT,          /* default vertical position   */
    CW_USEDEFAULT,          /* default width               */
    CW_USEDEFAULT,          /* default height              */
    (HWND) NULL,            /* no parent or owner window   */
    (HMENU) NULL,           /* class menu used             */
    hinstance,              /* instance handle             */
    NULL);                  /* no window creation data     */

if (!hwndMain)
    return FALSE;

/*
 * Show the window using the flag specified by the program
 * that launched the application, and send the application
 * a WM_PAINT message.
 */

ShowWindow(hwndMain, SW_SHOWDEFAULT);
UpdateWindow(hwndMain);

.
. /* Start the message loop for the application. */
.

上記の例では、 メイン ウィンドウを作成した後にShowWindow関数を呼び出していることに注意してください。Windowsはメイン ウィンドウの作成後に自動的にメイン ウィンドウを表示しないため、 この呼び出しが必要です。SW_SHOWDEFAULTをShowWindowに渡すことにより、 アプリケーションを起動したプログラムがメイン ウィンドウの初期表示状態を設定することが可能になります。UpdateWindow関数は、 最初のWM_PAINTメッセージをウィンドウに送ります。

 

子ウィンドウの作成、 列挙、 およびサイズ変更の方法

ウィンドウのクライアント領域をいくつかの領域に機能的に分割するには、 子ウィンドウを使います。子ウィンドウは、 メイン ウィンドウの場合と同様にCreateWindowEx関数を使って作成します。アプリケーション定義のウィンドウ クラスに属するウィンドウを作成するには、 子ウィンドウを作成する前に、 ウィンドウ クラスを登録し、 ウィンドウ プロシージャを用意しなければなりません。子ウィンドウには、 作成時にWS_CHILDスタイルを付け、 親ウィンドウを指定します。

次の例では、 サイズの同じ3つの子ウィンドウを作成して、 アプリケーションのメイン ウィンドウのクライアント領域を機能的に3つの領域に分割しています。各子ウィンドウは、 メイン ウィンドウのクライアント領域と同じ高さと、 3分の1の幅を持ちます。メイン ウィンドウは、 WM_CREATEメッセージに応答して子ウィンドウを作成します。このメッセージは、 メイン ウィンドウが独自のウィンドウ作成処理を行っている間に受け取ります。各子ウィンドウはWS_BORDERスタイルを持っているため、 細い線の境界が付きます。また、 WS_VISIBLEスタイルが指定されていないため、 子ウィンドウはいずれも初期状態では表示されません。各子ウィンドウには子ウィンドウIDが割り当てられていることに注意してください。

メイン ウィンドウは、 WM_SIZEメッセージに応答して子ウィンドウのサイズと位置を設定します。このメッセージは、 メイン ウィンドウがサイズを変更するときに受け取ります。WM_SIZEに応答して、 メイン ウィンドウは自分のクライアント領域の寸法をGetWindowRect関数により取得した後、 その寸法をEnumChildWindows関数に渡しています。EnumChildWindowsは、 各子ウィンドウのハンドルを、 さらにアプリケーション定義のEnumChildProcコールバック関数に渡しています。このコールバック関数は、 MoveWindow関数を呼び出して各子ウィンドウのサイズと位置を設定しています。各子ウィンドウのサイズと位置は、 メイン ウィンドウのクライアント領域の寸法に基づいて計算され、 子ウィンドウのIDによって識別されます。最後に、 EnumChildProcはShowWindow関数を呼び出し、 ウィンドウを表示しています。
#define ID_FIRSTCHILD  100
#define ID_SECONDCHILD 101
#define ID_THIRDCHILD  102

LONG APIENTRY MainWndProc(hwnd, uMsg, wParam, lParam)
HWND hwnd;
UINT uMsg;
UINT wParam;
LONG lParam;
{
    RECT rcClient;
    int i;

    switch(uMsg) {
        case WM_CREATE: /* creating main window */

            /* Create three invisible child windows. */

            for (i = 0; i < 3; i++)
                CreateWindowEx(
                    0,
                    "ChildWClass",
                    (LPCTSTR) NULL,
                    WS_CHILD | WS_BORDER,
                    0,0,0,0,
                    hwnd,
                    (HMENU) (int) (ID_FIRSTCHILD + i),
                    hinst,
                    NULL);

            return 0;

        case WM_SIZE: /* main window changed size */

            /*
             * Get the dimensions of the main window's client
             * area, and enumerate the child windows. Pass the
             * dimensions to the child windows during enumeration.
             */

            GetClientRect(hwnd, &rcClient);
            EnumChildWindows(hwnd, EnumChildProc,
                (LPARAM) &rcClient);
            return 0;
        .
        . /* Process other messages. */
        .

    }
    return DefWindowProc(hwnd, uMsg, wParam, lParam);
}

BOOL CALLBACK EnumChildProc(hwndChild, lParam)
HWND hwndChild;
LPARAM lParam;
{
    LPRECT rcParent;
    int i, idChild;

    /*
     * Retrieve the child-window identifier. Use it to set the
     * position of the child window.
     */

    idChild = GetWindowLong(hwndChild, GWL_ID);

    if (idChild == ID_FIRSTCHILD)
        i = 0;
    else if (idChild == ID_SECONDCHILD)
        i = 1;
    else
        i = 2;

    /* Size and position the child window. */

    rcParent = (LPRECT) lParam;
    MoveWindow(hwndChild,
        (rcParent->right / 3) * i,
        0,
        rcParent->right / 3,
        rcParent->bottom,
        TRUE);

    /* Make sure the child window is visible. */

    ShowWindow(hwndChild, SW_SHOW);

    return TRUE;
}
 

ウィンドウを破棄する方法

ウィンドウを破棄するには、 DestroyWindow関数を使います。通常は、 ウィンドウを破棄する前に、 アプリケーションはWM_CLOSEメッセージを送り、 ウィンドウを破棄してもよいかどうかをユーザーに確認してもらう機会をウィンドウに与えます。コントロール メニューを持つウィンドウは、 ユーザーがそこから[閉じる]コマンドを選んだときに、 自動的にWM_CLOSEメッセージを受け取ります。ユーザーがウィンドウを破棄してもよいと確定した場合は、 DestroyWindowを呼び出します。Windowsは、 ウィンドウが画面から削除された後に、 WM_DESTROYメッセージをウィンドウに送ります。このメッセージに応答して、 ウィンドウは自分のデータを保存して、 割り当てていたリソースをすべて解放します。メイン ウィンドウはPostQuitMessage関数を呼び出してWM_DESTROYの処理を終え、 アプリケーションを終了させます。

次の例は、 ウィンドウを破棄する前にそのことをユーザーに確認してもらう方法を示したものです。この例では、 WM_CLOSEメッセージに応答して、 [はい]、 [OK]、 [キャンセル]の3つのボタンを持つダイアログ ボックスを表示させています。ユーザーが[はい]ボタンをクリックすると、 DestroyWindowが呼び出されます。それ以外のボタンをクリックした場合は、 ウィンドウは破棄されません。破棄されているウィンドウはメイン ウィンドウであるため、 この例ではWM_DESTROYメッセージに応答してPostQuitMessageを呼び出しています。
case WM_CLOSE:

    /*
     * Create the message box. If the user clicks
     * the Yes button, destroy the main window.
     */

    if (MessageBox(hwnd, szConfirm, szAppName,
            MB_YESNOCANCEL) == IDYES)
        DestroyWindow(hwndMain);
    else
        return 0;

case WM_DESTROY:

    /*
     * Post the WM_QUIT message to
     * quit the application terminate.
     */

    PostQuitMessage(0);
    return 0;

 

ウィンドウ関数とメッセージ

ウィンドウの作成と管理を行う関数およびメッセージを、 次に示します。

関数      
AdjustWindowRect      
AdjustWindowRectEx      
AnyPopup      
BeginDeferWindowPos      
BringWindowToTop      
ChildWindowFromPoint      
CloseWindow      
CreateWindow      
CreateWindowEx      
DeferWindowPos      
DestroyWindow      
EnableWindow      
EndDeferWindowPos      
EnumChildProc      
EnumChildWindows      
EnumThreadWindows      
EnumThreadWndProc      
EnumWindows      
EnumWindowsProc      
FindWindow      
GetClientRect      
GetDesktopWindow      
GetForegroundWindow      
GetLastActivePopup      
GetNextWindow      
GetParent      
GetTopWindow      
GetWindow      
GetWindowPlacement      
GetWindowRect      
GetWindowText      
GetWindowTextLength      
GetWindowThreadProcessId      
IsChild      
IsWindow      
IsWindowUnicode      
IsWindowVisible      
IsZoomed      
MoveWindow      
SetForegroundWindow      
SetParent      
SetWindowLong      
SetWindowPlacement      
SetWindowPos      
SetWindowText      
ShowOwnedPopups      
ShowWindow      
WindowFromPoint      
WinMain      
       
使われなくなったか、 または削除された関数      
EnumTaskWindows      
GetSysModalWindow      
GetWindowTask      
SetSysModalWindow      

メッセージ
WM_ACTIVATE
WM_ACTIVATEAPP
WM_CANCELMODE
WM_CHILDACTIVATE
WM_CLOSE
WM_COPYDATA
WM_CREATE
WM_DESTROY
WM_ENABLE
WM_ENDSESSION
WM_GETMINMAXINFO
WM_GETTEXT
WM_MOVE
WM_NCACTIVATE
WM_NCCALCSIZE
WM_NCCREATE
WM_NCDESTROY
WM_PARENTNOTIFY
WM_POWER
WM_QUERYENDSESSION
WM_QUERYOPEN
WM_QUIT
WM_SETTEXT
WM_SHOWWINDOW
WM_SIZE
WM_WINDOWPOSCHANGED
WM_WINDOWPOSCHANGING

▲ページトップに戻る

【本を読んでもよくらからない】 … 個別指導でわかりやすくお教えします
inserted by FC2 system