BizDesginerでの開発2-003 (gooブログBackup)

次に、数量*単価の計算と、合計の計算をしていきます。
その前に前回のロジック OnTitleDClickedOnRClicked ですが、FlexView1オブジェクトの直下に定義していました。TitleDClickedとかRClickedとかのイベントは本来 FlexTextBoxオブジェクトから発生するので、素直に作るとFlexTextBox1,2,3,4,5それぞれのところにロジックをおくということになります。しかし、そんなことをすると冗長すぎますので、イベントは上位オブジェクトに向かって伝搬するというCRSプログラムの法則を利用します。
FlexView1オブジェクト直下におけば、下位オブジェクトのイベントは全てcatchできるということです。
同じように、数量*単価の計算をFlexView1オブジェクト直下におきます。

Function OnTextChanged(e){
e.Row.FlexTextBox5 = e.Row.FlexTextBox3*e.Row.FlexTextBox4;
}

また、FlexTextBox3,FlexTextBox4,FlexTextBox5はnumber型に変更します。また金額は修正できないようにするため、FlexLabelに変更します

FlexTextBox:number FlexTextBox3 {
Title = "単価";
}
FlexTextBox:number FlexTextBox4 {
Title = "数量";
Width = 50;
}
FlexLabel:number FlexTextBox5 {
Title = "金額";
}

Form配列やSpreadの場合、
value = FlexTextBox3*FlexTextBox4;のような記述ができますが、FlexViewの場合、表示オブジェクトと実データのオブジェクトが違うので(この辺がForm配列とSpreadとかとの違い。たとえばFlexTextBoxオブジェクトとFlexTextBoxCellオブジェクト)、TextChangedイベントハンドラ内に記述します。
また、合計を計算するロジックもFlexView1オブジェクト直下に定義します。

Function OnCountTotal(e){
var su=0;
var kin=0;
var crow=FlexView1.GetRow();
while(!crow.End){
su += crow.FlexTextBox4;
kin += crow.FlexTextBox5;
crow.MoveNext();
}
^.TextBox2= su;
^.TextBox3= kin;
}

OnCountTotal (e)という名前にしていますが、別にHogeHoge(e)でもかまいません。Onなんとかという関数名にするとプロパティビューのイベントタブのところに表示されるようになるので、ちょっと便利な裏機能としてCV.netでは昔から活用していました。その習慣がいまでも残っているので、だいたいOnなんとかという名前をつけています。
また、オブジェクト定義の直前にコメント文を書くと、プロパティビューの下にあるコメントという箇所にその内容が表示されるようになります。
合計計算をやり直さないといけない場合は、明細の数量、単価が変わった場合と、行が削除された場合なので、TextChangedイベントハンドラとRClickedイベントハンドラを修正します。

Function OnTextChanged(e){
e.Row.FlexTextBox5 = e.Row.FlexTextBox3*e.Row.FlexTextBox4;
OnCountTotal(e);
}
・・・・・
Function OnRClicked(e){
var i=popupMenu("現在行の上に挿入","現在行を削除");
if (i==1){
FlexView1.InsertRow(1,e.Row);
}
else if (i==2){
FlexView1.DeleteRow(e.Row);
OnCountTotal(e);
}
}

あとは、日付のデフォルト値が空白なので、今日の日付を代入しておきます。

DateEdit DateEdit1 {
X = 89;
Y = 15;
Width = 95;
Height = 20;
Value = sysdate();
}

ところで、Biz/Designerでデザインをする際、FlexViewやSpreadなどは明細行が表示されていないので、とてもデザインしづらいのです。
そこで、FlexView1オブジェクト直下に、

if ($DESIGNTIME){
this << new CSVDocument << CSV{
111,222,33,45,66
111,222,33,45,66
111,222,33,45,66
};
}

と記述すると、デザイン時のみ、ダミーの明細行が表示されるようになります。
こうするとデザインしやすくなるので、CV.netではFlexViewやSpreadなどを使う場合、デザイン時のみ走るコードを埋め込んでCRSを作成しています。
あとは、色などを変更すれば、以下のような画面が出来上がりです。

最後に、このCRSスクリプトの全ソースを掲載します。

Form Form2 {
X = 0;
Y = 0;
Width = 510;
Height = 460;
BgColor = $CCCCFF;
Label Label1 {
X = 20;
Y = 15;
Width = 54;
Height = 21;
Value = "入力日";
BgColor = $CCFFCC;
}
DateEdit DateEdit1 {
X = 89;
Y = 15;
Width = 95;
Height = 20;
Value = sysdate();
}
Label Label2 {
X = 20;
Y = 42;
Width = 67;
Height = 20;
Value = "顧客コード";
BgColor = $CCFFCC;
}
ComboBox ComboBox1 {
X = 89;
Y = 42;
Width = 326;
Height = 19;
ComboItem ComboItem1[0];
}
Label Label3 {
X = 20;
Y = 70;
Width = 59;
Height = 18;
Value = "備考";
BgColor = $CCFFCC;
}
TextBox TextBox1 {
X = 89;
Y = 70;
Width = 404;
Height = 18;
}
Label Label4 {
X = 20;
Y = 91;
Width = 69;
Height = 19;
Value = "合計数量";
BgColor = $CCFFCC;
}
TextBox:number TextBox2 {
X = 89;
Y = 91;
Width = 80;
Height = 18;
}
Label Label5 {
X = 216;
Y = 91;
Width = 85;
Height = 16;
Value = "合計金額";
BgColor = $CCFFCC;
}
TextBox:number TextBox3 {
X = 302;
Y = 91;
Width = 108;
Height = 19;
}
FlexView FlexView1 {
X = 13;
Y = 119;
Width = 484;
Height = 309;
FlexRecord FlexRecord1 {
FlexTextBox FlexTextBox1 {
Title = "商品CD";
Width = 80;
TitleBgColor = $0000CC;
TitleFgColor = 18;

}
FlexTextBox FlexTextBox2 {
Title = "商品名";
Width = 120;
TitleBgColor = $0000CC;
TitleFgColor = 18;
}
FlexTextBox:number FlexTextBox3 {
Title = "単価";
TitleBgColor = $0000CC;
TitleFgColor = 18;
}
FlexTextBox:number FlexTextBox4 {
Title = "数量";
Width = 50;
TitleBgColor = $0000CC;
TitleFgColor = 18;
}
FlexLabel:number FlexTextBox5 {
Title = "金額";
TitleBgColor = $0000CC;
TitleFgColor = 18;
}
}
Function OnTitleDClicked(e){
FlexView1.InsertRow(1);
}
Function OnRClicked(e){
var i=popupMenu("現在行の上に挿入","現在行を削除");
if (i==1){
FlexView1.InsertRow(1,e.Row);
}
else if (i==2){
FlexView1.DeleteRow(e.Row);
OnCountTotal(e);
}
}
Function OnTextChanged(e){
e.Row.FlexTextBox5 = e.Row.FlexTextBox3*e.Row.FlexTextBox4;
OnCountTotal(e);
}
Function OnCountTotal(e){
var su=0;
var kin=0;
var crow=FlexView1.GetRow();
while(!crow.End){
su += crow.FlexTextBox4;
kin += crow.FlexTextBox5;
crow.MoveNext();
}
^.TextBox2= su;
^.TextBox3= kin;
}
if ($DESIGNTIME){
this << new CSVDocument << CSV{
111,222,33,45,66
111,222,33,45,66
111,222,33,45,66
};
}
}
Button Button1 {
X = 406;
Y = 432;
Width = 93;
Height = 24;
Title = "終了";
Function OnTouch(e){
//.Delete();
}
}
if ( !$DESIGNTIME ) {
/* ここに初期化処理を記述してください */
}
}