[ |../../index.htm#lansa/l4wdev06_0570.htm]
現在地:

2.14.3 2 つのフォームからなるアプリケーションの作成

このセクションでは、アプリケーションの作成方法について説明します。
ステップ1.最初に2つのフォームを作成する
2つの別々のフォームを作成することから開始しました。1つめは、WRKEMPという名前で、もう1つは、FRMDETAILという名前です。フォームは、作成されたときに、グループDemonstration Materialに保存されました。

名前

WRKEMP

説明

Work with Employees

グループ

Demonstration Material

 
すべてのフォームを同じグループまたはフレームワークに置くとアプリケーションが簡単に管理できます。アプリケーションにはグループを作成できます。 
それからエディターでフォームのユーザー・インターフェースと基本的な機能を設計します。 
1.      WRKEMPのキャプションを「Work with Employees」(社員の処理)にし、社員の詳細のリスト・ビューを作成します。メニュー・オプションとメニューを追加します。
2.      フォームのInitializeイベントにリストを埋め込むロジックを記述します。
3.      FRMDETAILのキャプションを「Employee Details」(社員の詳細)にし、社員の住所情報を表示するフィールドを追加します。 
4.      2つのコマンド・ボタンを追加します。OKコマンド・ボタンのClickイベントは、社員の詳細を更新してフォームを閉じ、キャンセルボタンのClickイベントは、フォームを閉じるだけです。
ここで各フォームを作成します。これがマルチフォーム・アプリケーションを作成する最初のステップです。 
ステップ2.Employee DetailsフォームをWork with Employeesフォームに含める
WRKEMPをアプリケーションのメイン・フォームにします。マルチフォーム・アプリケーションを作成する場合は、メイン・フォームが必要です。アプリケーションが実行されると、メイン・フォームは、他のフォームのプロパティを設定したり、メソッドを呼び出したり、イベントに応答することにより、アプリケーションの他のフォームを制御できます。
エディターでWRKEMPを開きます。リポジトリタブのグループタブのDEMONSTRATIONグループを開きます。このグループには、このグループに保存されているすべてのフォームが表示されます。
!worddavaf485e25f57cd86bb5b0fc63f3f1b1cc.png|height=32,width=32!
 
FRMDETAILを開いているフォームにドラッグし、FRMDETAILフォームをWRKEMPに追加します。以下のコンポーネント定義ステートメントが自動的に追加されます。
DEFINE_COM CLASS(#FRMDETAIL) NAME(#FRMDETAIL) HEIGHT(296) LEFT(326) TOP(172) WIDTH(494)
 
これでアプリケーションの基本構造を作成できました。WRKEMPは、FRMDETAILを所有するメイン・フォームです。 
WRKEMPは、FRMDETAILのオーナー・フォームとも呼ばれます。同様に、FRMDETAILは、WRKEMPのメンバー・フォームと呼ばれます。
これでFRMDETAILは、\[アウトライン\]タブの#WRKEMPのメンバー・コンポーネントとして表示されます。
オーナー・フォームとメンバー・フォーム 
オーナー・フォームにフォームを置く場合は、実際にはフォームのインスタンスが置かれます(インスタンスの詳細は、「[<span style="color: #0000ee"><span style="text-decoration: underline; ">2.2 コンポーネントの基本</span></span>|l4wdev06_0020.htm#_Ref436717670]」を参照してください)。つまり、以下のようになります。

複数のフォームの操作
フォームを作成したので、両方をエディターで開き、\[アウトライン\]タブを使用してフォーム間を移動します。
フォーム間の通信を確立する
アプリケーションが実行されると、2つのフォームの通信が確立されます。オーナー・フォームは、他のフォームのプロパティ、メソッド、イベントを使用して他のフォームを制御できます。
オーナー・フォームWRKEMPでは、以下のことができます。

WRKEMPは、FRMDETAILの内部を見ることはできません。
重要なことですが、WRKEMPは、FRMDETAILフォームそのもののプロパティ、メソッド、イベントを使用できますが、フィールドの内容を使用、制御することはできません。
例では、WRKEMPはFRMDETAILの#EMPNOフィールドの値を設定または取得できず、OKまたはキャンセルボタンについても情報を持ちません。
標準フォームのプロパティ、イベント、およびメソッド
すべてのフォームは、以下の標準のプロパティ、メソッド、およびイベントを持ちます。

プロパティ

Height、Width、Top、Left、Captionなど

メソッド

ActivatForm、CloseForm、CloseFormQuery、HideForm、ShowForm、ShowModalForm、MinimizeForm、MaximizeForm、RestoreForm

イベント

Activate、Closing、CloseQuery、Deactivate、GotFocus、Initialize、LostFocus

 
例えば、オーナー・フォームのWRKEMPフォームは、FRMDETAILの標準のプロパティ、メソッド、およびイベントを使用して以下のことができます。

SET com(#frmdetail) left(37) top(14)
 

invoke #frmdetail.ShowForm
 

EVTROUTINE HANDLING(#frmdetail.Closing)
   << 処理 >>
ENDROUTINE
 
ただし、上のすべてのうち、サンプル・アプリケーションで必要なのはShowFormメソッドとCloseFormメソッドだけです。
さらに、これらの標準プロパティ、メソッド、イベントのいずれもアプリケーションで必要なフォーム間の通信を確立する手段を提供するものではありません。そのため、FRMDETAILに対して追加のユーザー定義のプロパティ、メソッド、およびイベントを定義します。
FRMDETAILで必要なユーザー定義のプロパティ、イベント、メソッド
WRKEMPで以下のことができるよう、FRMDETAILではユーザー定義のプロパティ、メソッド、およびイベントが必要です。

例えば、オーナー・フォームのWRKEMPは、メンバー・フォームのプロパティ、メソッド、およびイベントを使用できるので、すべての変更はFRMDETAILに行います。FRMDETAILが使用できないので、WRKEMPにプロパティ、メソッド、およびイベントは追加されません。
ステップ3.ユーザー定義のプロパティ、メソッド、およびイベントをFRMDETAILに追加する
このセクションでは、ユーザー定義のプロパティ、メソッド、およびイベントをFRMDETAILに追加した方法を説明します。
3a.EmployeeプロパティをFRMDETAILに追加する
WRKEMPからFRMDETAILに社員番号を渡せるようにするには、FRMDETAILにEmployeeというユーザー定義のプロパティを作成します。以下のステートメントを追加して定義します。
Define_pty name(Employee) set(*auto #empno) get(*auto #empno) 
 
このステートメントは、FRMDETAILが実行時にオーナー・フォームによって設定または取得できるEmployeeプロパティを持つことを指定します。SETパラメータは、このプロパティに渡される値が自動的にFRMDETAILの#EMPNOフィールドに割り当てられることを指定します。GETパラメータはオーナー・フォームがEmployeeプロパティの値を検索すると、現在のFRMDETAILの#EMPNOフィールドの値が返されることを指定します。
3b.GetInfoメソッドをFRMDETAILに追加する
現在の社員の詳細の取得を要求できるよう、ユーザー定義のメソッドGetInfoをFRMDETAILに追加します。これは、FRMDETAILのメソッドの定義です。
mthroutine name(GetInfo)
   fetch fields(#detflds) from_file(pslmst) with_key(#empno)
endroutine  
FRMDETAILのイベントの1つにFETCHステートメントをなぜ置かないのか気になるかもしれません。その理由は、サンプル・アプリケーションでは、FRMDETAILのイベントでFETCHステートメントの実行に適したものがないということです。

3c.OKPressedイベントをFRMDETAILに追加する
FRMDETAILのOKボタンがクリックされたことを知らせるには、以下のようにFRMDETAILにカスタム定義のイベントを指定します。
define_evt name(OKPressed)
 
#OKBTNのClickイベントにSIGNALステートメントを追加することにより、FRMDETAILでOKボタンがクリックされたときにこのイベントが通知されるように指定されます。
EVTROUTINE HANDLING(#OKBTN.Click)
   signal event(OKPressed)
ENDROUTINE
 
これでFRMDETAILで#OKBTN.Clickイベントがトリガーされるたびにオーナー・フォームにOKPressedイベントが通知されます。
FRMDETAILの変更
変更の結果として、現在FRMDETAILにはWRKEMPと通信するためにWRKEMPから使用されるユーザー定義のプロパティ、メソッド、およびイベントがあります。
 

プロパティEMPLOYEE
 

FRMDETAILの#EMPNOフィールドの値を設定または取得するために使用される
Define_pty name(employee) set(*auto #empno) get(*auto #empno) 
 

メソッドGETINFO
 

FRMDETAILに選択した社員の詳細を取得させるために使用される
mthroutine name(GetInfo)
  fetch fields(#detflds) from_file(pslmst) with_key(#empno)
endroutine  
 

イベントOKPRESSED
 

他のフォームにFRMDETAILでOKボタンが押されたことを通知する
define_evt name(OKPressed)
signal event(OKPressed)

 
You may want to have a look at the Source Code for the Multi-Form Example Forms.
FRMDETAILに追加されたこれらのプロパティ、メソッド、およびイベントは、このサンプル・アプリケーションでは特にWRKEMPに使用されますが、もちろん、FRMDETAILが含まれる他のフォームでも使用できます。つまり、例えば、FRMDETAILが含まれる他のアプリケーションを作成した場合は、これらのプロパティ、メソッド、およびイベントはそのアプリケーションのオーナー・フォームから使用できます。
ステップ4.FRMDETAILと通信できるようにWRKEMPを変更する
FRMDETAILと通信できるようにWRKEMPを変更します。
4a.FRMDETAILを表示する
ユーザーがリストから社員を選択し、次に社員メニューの詳細オプションを選択したときに、FRMDETAILフォームを表示します。そのため、WRKEMPの詳細メニュー・アイテム(MDETAILS)のClickイベントにこのステートメントを追加します。
EVTROUTINE HANDLING(#MDetails.Click)    SET COM(#frmdetail) formowner(#com_owner)    invoke #frmdetail.ShowForm ENDROUTINE
 
ShowFormメソッドは、指定されたフォームを表示し、デスクトップでアクティブなウィンドウにします。
メンバー・フォームを表示する前に、実行時のFORMOWNERプロパティを使用してオーナー・フォームを常に明示で設定することをお勧めします。これはアプリケーションの基本構造に関係なく、デフォルトでアプリケーションで実行する最初のフォームがアプリケーションのすべてのメンバー・フォームのオーナーになるからです。複雑なアプリケーションでは、オーナー・フォームを設定しないと、予期しない結果が発生する場合があります。
4b.Employeeプロパティを設定する
また、FRMDETAILが表示されたらすぐにEmployeeプロパティの値を設定する必要がありました。そのため、詳細メニュー・アイテムのClickイベントにSETステートメントを以下のように追加します。
EVTROUTINE HANDLING(#MDetails.Click)
   SET COM(#frmdetail) formowner(#com_owner)
   invoke #frmdetail.ShowForm
    set com(#frmdetail) employee(#empno)
ENDROUTINE
これで現在の社員番号がWRKEMPからFRMDETAILに渡されます。
サンプル・アプリケーションでは実行しませんが、Employeeプロパティの値を以下のように設定することもできました。
set com(#frmdetail) employee('A0070')
 
また、以下のようにEmployeeの値を取得することもできます。
CHANGE FIELD(#EMPNO) TO(#FRMDETAIL.Employee)
 
4c.現在の社員の詳細を取得する
Employeeプロパティの値を設定するだけでなく、FRMDETAILに現在の社員の詳細を取得させる必要もありました。再度詳細メニュー・アイテムのClickイベントにステートメントを以下のように追加します。
EVTROUTINE HANDLING(#MDetails.Click)
   SET COM(#frmdetail) formowner(#com_owner)
   invoke #frmdetail.ShowForm
   set com(#frmdetail) employee(#empno)
   invoke #frmdetail.GetInfo
ENDROUTINE
4d.OKPressedイベントに対応する
FRMDETAILでOKボタンがクリックされたときにWRKEMPの社員のリストを更新するために、OKPressedイベントを監視するためのイベント・ルーチンを作成しました。
EVTROUTINE HANDLING(#frmdetail.OKPressed)
      execute GetList
ENDROUTINE
 
FRMDETAILでOKボタンが押されるたびにWRKEMPでGetListサブルーチンが実行されます。
2.14.7 マルチフォーム・アプリケーション例のソース・コード 」も参照してください。
メソッドについて注意すること
例が完成する前は、フォームがメソッドを呼び出せても何の意味もありません。そのため、OKボタンまたはキャンセルボタンのClickイベントにFRMDETAILのCloseFormメソッドを置くことを選択しました。
EVTROUTINE HANDLING(#CANCELBTN.Click)    invoke #frmdetail.Closeform ENDROUTINE   EVTROUTINE HANDLING(#OKBTN.Click)    UPDATE FIELDS(#DETFLDS) IN_FILE(PSLMST) WITH_KEY(#EMPNO) ISSUE_MSG(*YES)    invoke #frmdetail.Closeform    signal event(OKPressed) ENDROUTINE
 
もちろん、WRKEMPからメソッドを呼び出すこともできましたが、この場合、キャンセルボタンがクリックされたことを通知するイベントを作成する必要がありました。
フォームをコンパイルする
これでアプリケーションは完成しました。両方のフォームを保存してコンパイルします。最初にカスタム定義のプロパティが認識されるよう、FRMDETAILを保存してコンパイルしました。それからWRKEMPをコンパイルしました。
これ以外の実装方法
サンプル・アプリケーションを少し異なる方法で実装できます。

[ |../../index.htm#lansa/l4wdev06_0570.htm]