IBM i (旧AS400）の自己学習メモ１０　DSPF　SDA（Screen Design Aid）チートシート

# 自己学習メモインデックス

[IBM i (旧AS400）の自己学習メモ　インデックス](https://qiita.com/You_name_is_YU/items/3964849e7803c8eaf767)

# 概要

DDSの画面ファイル（DSPF）を開発する際に利用するSEUとは別に使うSDA（Screen Design Aid）も使い方を覚えないと全く何をしたらいいのか分からないため、使い方を理解するためチートシートを作成します。
自分は初心者なので、随時必要なものを更新しながら使いこなせるようになろうと思っています。
内容に誤りがある場合は、重要なポイントなど漏れていましたらご指摘いただけますと幸いです。

# チートシート

## DSPFファイルの新規作成

メンバー一覧画面でF6キーを押下し、新規でソースコードを作成する画面を表示して、Source typeに`DSPF`と指定するとDSPFファイルを新規作成できます。

```shell
                      Start Source Entry Utility (STRSEU)     
                                                              
Type choices, press Enter.                                    
                                                              
Source file  . . . . . . . . . . SRCFILE      > QDSPSRC       
  Library  . . . . . . . . . . .              >   YAMAGUCHI1  
Source member  . . . . . . . . . SRCMBR         DSP01         
Source type  . . . . . . . . . . TYPE           DSPF          
Text 'description' . . . . . . . TEXT           *BLANK        
```

## SDAの実行

メンバー一覧画面でDSPFファイルのOPTに`17`(Change using SDA)を指定してEnterを押下すると`Work with Display Records`という画面が表示される。
新規作成時はDisplay Recordsが未作成なので、Optに`1`(Add)を指定してEnterを押下するとAdd New Record画面が表示される。
New Recordの名前を任意で指定してEnterを押下するとSDAの画面が表示される。

![AS400-2.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/246556/2dd09461-4fad-c3e9-edb5-9996a199a8e3.gif)

## ラベルの操作

### ラベルの設置

シングルクォートで括った任意の文字列を指定した場所に表示する。
※シングルクォートで括らないと、別々のフィールドとして認識されてしまうので注意が必要だ。

|コマンド|例|
|:--|:--|
|シングルクォートで括った文字列を１つのラベルとして設置する。|'Sample Title'|

![AS400-2.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/246556/e2fcfdfd-df51-9cd3-cb7b-3969da908bed.gif)

### ラベルの削除

|コマンド|例|
|:--|:--|
|削除対象のラベルの先頭に`d`と入力|d|

### ラベルの位置調整

|コマンド|例|
|:--|:--|
|acとラベルの先頭に入力することで、ラベルの位置を中央に揃える。|Sample Titleラベルの場合→<br>acample Titleと入力|
|ラベルの左に入力した`<`の数だけ左にずらす。|<Sample Title<br><<<<Sample Title|
|ラベルの右に入力した`>`の数だけ右にずらす。|Sample Title><br>Sample Title>>>>|

![AS400-2.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/246556/fb00447b-0190-68d0-7dc6-65fd64f5d3e1.gif)

|コマンド|例|
|:--|:--|
|`-`でラベルを挟み、移動先の先頭に`=`と入力すると指定した場所にラベルを移動する。|-Sample Title-<br>=|

![AS400-2.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/246556/8fd47270-075e-4eb2-0cbc-8c5d8c3a10df.gif)

### ラベルの色変更

|コマンド|例|
|:--|:--|
|agでGreen|ag|
|awでWhite |aw|
|arでRed|ar|
|atでTurquoise|at|
|ayでYellow|ay|
|apでPink|ap|
|abでBlue|ab|

※一度変更した色のフィールドを、別の色に変更しようとしてもコマンドが受け付けられないようです。
　方法としては、arでRedにした後、-arで元に戻し、ayなど別の色に変更することで対処できます。

![AS400-2.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/246556/f0e68cf0-8ada-32f9-6034-ce284b2f0a9b.gif)



## フィールド操作

### フィールドの反転表示とタブ移動

|コマンド|備考|
|:--|:--|
|F20でフィールドの反転表示。|ラベルなどが１つのまとまったフィールドになっているのか、バラバラなのか判別する際に便利。|
|F18|各フィールドにタブで移動する。|

![AS400-2.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/246556/8c829a26-b785-b046-c5e9-ca55252e0d9f.gif)

### システム定数

システムで予め定数として定義されているフィールドです。

|コマンド|備考|
|:--|:--|
|*DATE|システム日付|
|*TIME|システム時刻|
|*USER|ログインユーザ名|

![AS400-2.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/246556/62b2dd16-52a1-631e-703a-c21efd1ce8ba.gif)

**補足**
`*DATE`と指定して、SDAから日付を画面フィールドとして定義すると「DD-DD-DD」というハイフン区切りの８桁にフォーマットされた日付形式となります。
SDA上では編集する方法がわからなかったのですが、SEUでDSPFファイルを以下のように編集することで、YYYY-MM-DD形式でシステム日付を表示することが可能なことがわかりました。

```shell
# 修正前
 FMT DP .....AAN01N02N03T.Name++++++RLen++TDpBLinPosFunctions+++++++++++++++++++++++++++
0001.30      A                                  1 70DATE                      
0001.40      A                                      EDTCDE(Y)                           

# 修正後
 FMT DP .....AAN01N02N03T.Name++++++RLen++TDpBLinPosFunctions+++++++++++++++++++++++++++
0001.30      A                                  1 70DATE(*JOB *YY)                      
0001.40      A                                      EDTCDE(Y)                           
```

*JOBの部分は、*SYSとしてもOK

- *JOB : ジョブ日付（省略時もこれ）
- *SYS : システム日付

### 出力／入力／入出力フィールド

#### 文字フィールド

|コマンド|備考|
|:--|:--|
|+に続けて必要な文字数分Iを打つ<br>又は+I(999)と括弧内に文字数を入力|入力専用の文字フィールド（Input）|
|+に続けて必要な文字数分Oを打つ<br>又は+O(999)と括弧内に文字数を入力|出力専用の文字フィールド（Output）|
|+に続けて必要な文字数分Bを打つ<br>又は+B(999)と括弧内に文字数を入力|入出力用の文字フィールド（Both）|

#### 数字フィールド

|コマンド|備考|
|:--|:--|
|+に続けて必要な文字数分3を打つ<br>又は+3(999)と括弧内に文字数を入力|入力専用の数字フィールド|
|+に続けて必要な文字数分6を打つ<br>又は+6(999)と括弧内に文字数を入力|出力専用の数字フィールド|
|+に続けて必要な文字数分9を打つ<br>又は+9(999)と括弧内に文字数を入力|入出力用の数字フィールド|

#### フィールドの識別名を設定

+IIIIIなどのように、入力や出力フィールドを定義しても、そのフィールドに識別名がついていないとプログラムから操作しづらくなってしまう。
フィールドの識別名を設定する方法は以下の通り。

|コマンド|備考|
|:--|:--|
|フィールドの先頭に`?`を入力し名前を変更|?入力後画面下部に表示されるエリアに識別名を入力する。|
|F4キーを押下して該当の項目に名前を入力|F4キーを押下するとフィールド一覧が表示されるので、まとめて識別名をセットする際に便利。|

### フィールドの属性設定・設定解除

```shell
Command                           Command                      
Add   Remove   Attribute          Add   Remove   Color         
                                                               
H     -H       High intensity     CB    -CB      Blue          
                                                               
R     -R       Reverse image      CG    -CG      Green         
                                                               
S     -S       Column             CP    -CP      Pink          
               separators                                      
B     -B       Blink              CR    -CR      Red          
                                                              
N     -N       Nondisplay         CT    -CT      Turquoise    
                                                              
U     -U       Underscore         CW    -CW      White        
                                                              
      -A       Remove all               -CA      Remove all   
               attributes                        colors       
                                                              
Note: Commands N, -N, S, -S are not available for menu        
      design function.                                        S
```

### データベースファイルからフィールドを設置

任意で画面の入出力項目を設置していくこともできるが、データベースファイルからそのフィールドに合わせたサイズで画面項目を設置することも可能です。

SDAの画面で`F10`を押下し、データベースファイル選択画面を表示。
Option/Database File/Library/Recordを指定してEnterを押下。

```shell
                             Select Database Files           
                                                             
 Type options and names, press Enter.                        
   1=Display database field list                             
   2=Select all fields for input (I)                         
   3=Select all fields for output (O)                        
   4=Select all fields for both (B) input and output         
                                                             
 Option    Database File   Library      Record               
   1        MTOKISKP       YAMAGUCHI1   MTOKISKR             
```                                                     

データベースフィールドの選択画面で対象となるフィールドのOptionを設定しEnter

```shell
                           Select Database Fields                           
                                                                            
Record . . . :   MTOKISKR                                                   
                                                                            
Type information, press Enter.                                              
  Number of fields to roll  . . . . . . . . . . . . . . . . . .     8       
  Name of field to search for . . . . . . . . . . . . . . . . .             
                                                                            
Type options, press Enter.                                                  
  1=Display extended field description                                      
  2=Select for input (I), 3=Select for output (O), 4=Select for both (B)    
                                                                            
Option  Field        Length   Type    Column Heading                        
  4     TOKCD             5    A      TOKCD                                 
  4     TOKNM            40    O      TOKNM                                 
  4     TOKKANA          80    A      TOKKANA                               
  4     TOKTEL           15    A      TOKTEL                                
```   

画面下部に以下のように表示される。

```shell
 1:TOKCD 2:TOKNM 3:TOKKANA 4:TOKTEL 
```

この項目を画面に設置したい場合、

```
&1
又は
&1L
```

と指定する。
Lをつけると、設置したフィールドの左側に、そのフィールドの名称が自動的にセットされます。

## F1キー〜F24キーのインジケータ

SDAで画面定義をしてデザインをしただけではF3キーで画面を終了する。などの動作も受け付けてくれないようです。
これらのキー操作を認識するにはF3キーなどに対応したインジケータ（CA01〜CA24）を設定する必要があります。

**補足**

F1〜F24キーのインジケータを指定する方法は、ここで述べているCA01〜CA24以外に、CF01〜CF24と指定する方法もあります。
以下違いです。

- CA (Command Attention)
    - 画面上の入力データがプログラムへ渡されません。
- CF (Command Function)
    - 画面上の入力データがプログラムへ渡されます。

まずレコード画面で対象のレコードのOptに`8`を入力

```shell
                     Work with Display Records                                
                                                                              
File  . . . . . . :   QDSPSRC                Member . . . . . . :   DSP01     
  Library . . . . :     YAMAGUCHI1           Source type  . . . :   DSPF      
                                                                              
Type options, press Enter.                                                    
  1=Add             2=Edit comments          3=Copy          4=Delete         
  7=Rename          8=Select keywords       12=Design image                   
                                                                              
Opt  Order    Record        Type      Related Subfile   Date        DDS Error 
                                                                              
8       10    PANEL01       RECORD                      20-04-14              
^                                                                              
```

Indicator keywordsに`Y`を入力

```shell
                           Select Record Keywords    
                                                     
Record . . . :   PANEL01                             
                                                     
Type choices, press Enter.                           
                                                     
                                    Y=Yes            
  General keywords  . . . . . . . .                  
  Indicator keywords  . . . . . . .   Y              
  Application help  . . . . . . . .                  
  Help keywords . . . . . . . . . .                  
  Output keywords . . . . . . . . .                  
  Input keywords  . . . . . . . . .                  
  Overlay keywords  . . . . . . . .                  
                                                     
  Print keywords  . . . . . . . . .                  
  ALTNAME keyword . . . . . . . . .                  
                                                     
  TEXT keyword  . . . . . . . . . .                  
                                                     
                                                     
                                                     
F3=Exit   F4=Display Selected Keywords   F12=Cancel  
```

ココではF3キーを押下した際のインジケータを設定しています。
F3キーに対応するKeywordはCA03です。
Indicators/+ Respの項目にある03はCA03のキー入力を受け付けた際に*ONとなる標識です。
（標識＝インジケータ？という理解でいいのか？？）

```shell
                          Define Indicator Keywords                          
                                                                             
Record . . . :   PANEL01                                                     
                                                                             
Type keywords and parameters, press Enter.                                   
  Conditioned keywords:       CFnn CAnn CLEAR PAGEDOWN/ROLLUP PAGEUP/ROLLDOWN
                              HOME HELP HLPRTN                               
  Unconditioned keywords:     INDTXT VLDCMDKEY SETOF CHANGE                  
                                                                             
Keyword   Indicators/+ Resp Text                                             
CA03                    03  終了                                           
```

## 任意の標識によるフィールドの表示切替

入力チェックを行って、エラーがあったときだけエラーメッセージを表示するようなケースがあると思います。
そのエラーメッセージは、ラベルとして画面に設置しておいて、普段は非表示となっているけれども、
エラーの時に任意の標識を*ONにして表示する例を示します。

1. 対象のフィールドの先頭に`*`
2. Display attributesに`Y`
3. Field conditioningの項目に` 91`←標識を入力

![AS400-1.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/246556/ad331fcf-2a46-1117-2840-ba9ad489ec6e.gif)

この設定をすると、91の標識が*ONの時だけエラーメッセージが画面に表示されるようになります。

## 罫線を引く（GRDRCD/GRDLIN）

DSPFで罫線を引く方法として、ここではGRDRCDというレコードを作って、GRDLINで罫線を引いていきます。
TOOLBOXという便利なものを使うと、ドラッグ＆ドロップで罫線が引けたりするようですが、
PUB400.comにはそういった便利機能が備わっておらず、ソースコードにごりごり書いていくスタイルだったら罫線が引けたので、その内容をメモします。

SDAでグラフィカルに設定するのではなく、DSPFファイルをSEUで開いてごりごりソースコードに直書きする感じです。
しかもSEUでF4キーを押下してプロンプトでいい感じに入力することもできず、ひたすらごりごりソースコードに書きます。

手順としては

1. 任意の名前のType：RECORDをSDAの機能で作成<br>**※GRDRCDというTypeで新規レコードが作れないので一旦RECORDで新規作成**
2. SDAの画面に１つもフィールドを設置しないと保存して終了できなかったので、適当になんでもいいのでフィールドを１つ設置してF3で終了
3. DSPFファイルのOPTに`2`を入力してSEUの画面に遷移
4. 以下のような定義をする

```shell:DSPFのSEUの画面
 FMT DP .....AAN01N02N03T.Name++++++RLen++TDpBLinPosFunctions+++++++++++++++++++++++++++
0003.70      A          R KSEN                      GRDRCD                              
0003.80      A*%%TS  SD  20200416  100413  YAMAGUCHI   REL-V7R4M0  5770-WDS             
0003.90      A** 仮で入力した値はコメントアウト  2'KEISEN'                            
0004.00      A                                      GRDATR((*COLOR HWHT))               
0005.00      A                                      GRDLIN((*POS (10 05 06)) +          
0006.00      A                                             (*TYPE  LEFT))               
0007.00      A                                      GRDLIN((*POS (10 05 75)) +          
0008.00      A                                             (*TYPE UPPER))               
0009.00      A                                      GRDLIN((*POS (10 79 06)) +          
0010.00      A                                             (*TYPE RIGHT))               
0011.00      A                                      GRDLIN((*POS (15 05 75)) +          
0012.00      A                                             (*TYPE LOWER))               
0013.00      A                                      GRDLIN((*POS (10 28 06)) +          
0014.00      A                                             (*TYPE  LEFT))               
0015.00      A                                      GRDLIN((*POS (11 05 75)) +          
0016.00      A                                             (*TYPE LOWER))               
0017.00      A                                      GRDLIN((*POS (13 05 75)) +          
0018.00      A                                             (*TYPE LOWER))               
```

### 罫線をSEUでごりごりコーディングするポイント

通常画面のパーツであるRECORDと定義されているFUNCTION部分を`GRDRCD`に変更する。

```shell
0003.70      A          R KSEN                      GRDRCD
```

RECORDを新規で作った際、適当に用意したフィールドについては、不要となるのでコメントアウトする。

```shell
0003.90      A** 仮で入力した値はコメントアウト  2'KEISEN' 
```

GRDLINを使って罫線をごりごりコーディングしていく。

```shell
0005.00      A                                      GRDLIN((*POS (10 05 06)) +          
0006.00      A                                             (*TYPE  LEFT)) 
```

- *POS
    - 第１引数 ： 行番号
    - 第２引数 ： 列番号
    - 第３引数 ： 罫線の長さ
- *TYPE
    - LEFT ： 起点の左側に罫線を引く。罫線の長さで指定された分、下方向に伸びていく。
    - RIGHT ： 起点の右側に罫線を引く。
    - UPPER ： 起点の上側に罫線を引く。
    - LOWER ： 起点の下側に罫線を引く。

画面の起点を確認する方法としては、SDAの画面右下の行番号／列番号を確認するといいと思います。
<img width="1088" alt="スクリーンショット 2020-04-16 19.49.31.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/246556/2c71e55f-b02e-bc26-ae59-bb012d3f563f.png">