MFC ActiveX コントロール : ActiveX コントロールにおけるデータ連結の使用
更新 : 2007 年 11 月
ActiveX コントロールの強力な機能の 1 つとして、データ連結があります。データ連結を使うと、コントロールのプロパティをデータベースの特定のフィールドに連結できます。連結されたプロパティのデータをユーザーが変更すると、コントロールはそれをデータベースに通知し、レコード フィールドの更新を要求します。データベースは、要求が成功したか失敗したかをコントロールに通知します。
ここでは、コントロール側での処理について説明します。データベースとデータ連結のやり取りは、コントロール コンテナ側で実装する必要があります。データベースとのやり取りをコンテナで操作する方法については、ここでは触れていません。データ連結用にコントロールを準備する方法については、この項目の残りの部分で説明します。
データ連結コントロールの概念図
COleControl クラスには、データ連結を簡単に実装できるようにするためのメンバ関数が 2 つあります。1 つは BoundPropertyRequestEdit 関数で、プロパティ値の変更許可を要求するときに使います。もう 1 つは BoundPropertyChanged 関数で、プロパティ値が正常に変更されると呼び出されます。
ここでは、次のトピックについて説明します。
連結可能なストック プロパティの作成
連結可能な Get/Set メソッドの作成
連結可能なストック プロパティの作成
データ連結の実装手法としては、連結可能な get/set メソッドを作成する方が一般的ですが、データ連結ストック プロパティを作成することもできます。
メモ : |
---|
ストック プロパティには、既定で、bindable 属性と requestedit 属性が指定されています。 |
プロパティの追加ウィザードを使って連結可能なストック プロパティを追加するには
MFC ActiveX コントロール ウィザードを使って、プロジェクトを開始します。
コントロールのインターフェイス ノードを右クリックします。
ショートカット メニューが表示されます。
ショートカット メニューの [追加] をクリックし、[プロパティの追加] をクリックします。
[プロパティ名] ボックスからプロパティ名を選択します。たとえば、[Text] を選択します。
[Text] はストック プロパティなので、bindable 属性と requestedit 属性が既に設定されています。
[IDL 属性] タブの [displaybind] チェック ボックスと [defaultbind] チェック ボックスをオンにし、プロジェクトの .IDL ファイルのプロパティ定義に属性を追加します。これらの属性を指定すると、コントロールはユーザーから見えるようになり、ストック プロパティは既定の連結可能プロパティになります。
この段階では、コントロールはデータ ソースからのデータを表示できますが、ユーザーはデータ フィールドを変更することはできません。コントロールに表示されるデータを変更できるようにするには、OnOcmCommand 関数を次のように変更します。
#ifdef _WIN32
WORD wNotifyCode = HIWORD(wParam);
#else
WORD wNotifyCode = HIWORD(lParam);
#endif
if(wNotifyCode==EN_CHANGE)
{
if(!BoundPropertyRequestEdit(DISPID_TEXT))
{
SetNotSupported();
}
else
{
GetText();
// Notify container of change
BoundPropertyChanged(DISPID_TEXT);
}
}
return 0;
ここでプロジェクトをビルドすると、コントロールが登録されます。ダイアログ ボックスにコントロールを挿入すると、データ フィールドのプロパティとデータ ソースのプロパティが追加されて、コントロールに表示するデータ ソースとフィールドを選択できるようになります。
連結可能な Get/Set メソッドの作成
データ連結 get/set メソッドのほかに、連結可能なストック プロパティも作成できます。
メモ : |
---|
次の手順では、Windows コントロールをサブクラス化する ActiveX コントロール プロジェクトがあることを前提としています。 |
プロパティの追加ウィザードを使って連結可能な get/set メソッドを追加するには
コントロールのプロジェクトを読み込みます。
[コントロールの設定] ページで、どのウィンドウ クラスからコントロールをサブクラス化するかを選択します。たとえば、サブクラス化するクラスとして EDIT コントロールを指定します。
コントロールのプロジェクトを読み込みます。
コントロールのインターフェイス ノードを右クリックします。
ショートカット メニューが表示されます。
ショートカット メニューの [追加] をクリックし、[プロパティの追加] をクリックします。
[プロパティ名] ボックスにプロパティ名を入力します。この例では MyProp を使用します。
[プロパティの種類] ボックスでデータ型を選択します。この例では short を使用します。
実装の種類として、[Get/Set メソッド] をクリックします。
[IDL 属性] タブの [bindable]、[requestedit]、[displaybind]、および [defaultbind] の各チェック ボックスをオンにし、プロジェクトの .IDL ファイルのプロパティ定義に属性を追加します。これらの属性を指定すると、コントロールはユーザーから見えるようになり、ストック プロパティは既定の連結可能プロパティになります。
[完了] をクリックします。
SetMyProp 関数の本体に次のコードを追加します。
if(!BoundPropertyRequestEdit(1)) { SetNotSupported(); return; } else { if(AmbientUserMode()) // SendMessage only at run-time { _stprintf_s(m_strText.GetBuffer(10), 10, _T("%d"), newVal); SetWindowText(m_strText); m_strText.ReleaseBuffer(); } else { InvalidateControl(); } // Signal a property change // This is the MFC equivalent of OnChanged() BoundPropertyChanged(1); SetModifiedFlag(); }
BoundPropertyChanged 関数と BoundPropertyRequestEdit 関数に渡されるパラメータはプロパティの DISPID で、.IDL ファイル内のプロパティに対する id() 属性に渡されるパラメータです。
OnOcmCommand 関数に次のコードを追加します。
#ifdef _WIN32 WORD wNotifyCode = HIWORD(wParam); #else WORD wNotifyCode = HIWORD(lParam); #endif if(wNotifyCode==EN_CHANGE) { if(!BoundPropertyRequestEdit(DISPID_TEXT)) { SetNotSupported(); } else { GetText(); // Notify container of change BoundPropertyChanged(DISPID_TEXT); } } return 0;
OnDraw 関数に次のコードを追加します。
if(!AmbientUserMode()) { // Draw the Text property at design-time pdc->FillRect(rcBounds, CBrush::FromHandle((HBRUSH)GetStockObject(WHITE_BRUSH))); pdc->DrawText(m_strText, -1, (LPRECT)&rcBounds, DT_LEFT | DT_TOP | DT_SINGLELINE); } else { DoSuperclassPaint(pdc, rcBounds); }
コントロール クラスのヘッダー ファイルのパブリック セクションには、メンバ変数についての次の定義 (コンストラクタ) を追加します。
CString m_strText; short m_nMyNum;
DoPropExchange 関数の最後に次の行を追加します。
PX_String(pPX, _T("MyProp"), m_strText);
OnResetState 関数に次のコードを追加します。
COleControl::OnResetState(); // Resets defaults found in DoPropExchange m_strText = AmbientDisplayName();
GetMyProp 関数に次のコードを追加します。
if(AmbientUserMode()) { GetWindowText(m_strText); m_nMyNum = (short)_ttoi(m_strText); } return m_nMyNum;
ここでプロジェクトをビルドすると、コントロールが登録されます。ダイアログ ボックスにコントロールを挿入すると、データ フィールドのプロパティとデータ ソースのプロパティが追加されて、コントロールに表示するデータ ソースとフィールドを選択できるようになります。