【intra-mart】[IM-FormaDesigner]ユーザ選択アイテムと明細テーブルを連携し複数ユーザの選択ができるようにする


### やりたかったこと

IM-FormaDesignerの標準のユーザ選択アイテムでは、複数ユーザを選択することができません。
そこで、いつもながら、関数の書き換えを行い、各部品の挙動を変更することにしました。

* イベントボタン（ユーザ選択）で「ユーザ選択」ダイアログを表示し、対象ユーザを検索する
* ユーザ選択結果を明細テーブルに表示する
* イベントボタン（リセット）で明細テーブルのデータを削除する

### 成果物イメージ

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/93122/6f16f411-95cb-ab5c-782f-9aabe186f793.png)


### ダウンロード
* (ファイル名):forma_user_button_table_cooperation.zip
* URL: http://www.rinsymbol.sakura.ne.jp/intra-mart/003_user_button_table_cooperation/forma_user_button_table_cooperation.zip


* アクション設定

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/93122/2fe9c2aa-d771-55d1-1c50-4b9cac35a238.png)


### 対応の概要

#### ユーザ選択アイテムの関数を上書きし、挙動を変更

* forma.master.openSelectItemPage
  * ユーザ選択画面の呼び出し前の設定。デフォルトで単一選択となっている部分を複数選択に変更
        


```js:rewrite_forma_func.jsの40行目付近
        //-------------------------------------------------------------------------
        // ユーザ選択画面の選択タイプを複数選択に変更する
        //-------------------------------------------------------------------------
        forma.master.openSelectItemPage = function (item_id) {
            // 中略

            //単一選択を指定する場合
            // parameter.type = "single";
            //複数選択を指定する場合
            parameter.type = "multiple"; 


            // 中略
        };
```

#### ユーザ選択呼び出し後のコールバック関数の処理内容を変更

* forma.master.addItemSelectPageParams
    * resultオブジェクトにユーザ情報が格納されるため、取得
        * ユーザコード：result[n].data.user_cd
        * ユーザ名：result[n].data.user_name
    * 明細テーブルアイテムに設定されている情報と比較し、すでに追加済みユーザはマージ。

```js:rewrite_forma_func.jsの112行目付近
        forma.master.addItemSelectPageParams( userSelectItemId, userSelectKey, new Date(), tabs,
        // コールバック用の関数：ユーザ選択後に呼び出される
        function(result){
            var userList = [];
            result.forEach(function(obj){
                var userName = obj.data.user_name;
                var userCd = obj.data.user_cd;
                var userObj = {userCd: userCd, userName: userName};
                userList.push(userObj);
            });


                // 現在設定されているテーブル情報を取得
            var rowId = "";
            var inputIdList = [];
            inputIdList[0] = RNGD_APP_CONST.FIELD_ID_COLUMN01;
            inputIdList[1] = RNGD_APP_CONST.FIELD_ID_COLUMN02;
            var targetTbl = formaTblGetItemData(RNGD_APP_CONST.FIELD_ID_TABLE, rowId, inputIdList);


            // ユーザ選択で取得したユーザと、既存のデータをマージする
            var searchUserList = [];
            targetTbl.forEach(function(row) {
                var userCd = row[RNGD_APP_CONST.FIELD_ID_COLUMN01];
                var userName = row[RNGD_APP_CONST.FIELD_ID_COLUMN02];
                var userObj = {userCd: userCd, userName: userName};
                searchUserList.push(userObj);
            });
            userList = searchUserList.concat(userList);

            var targetIdList = [];
            var targetUserObjList = [];

            userList.forEach(function(user) {
                var targetUserCd = user.userCd;
                // 対象ユーザとして一度も追加されていない場合のみ
                if(targetIdList.indexOf(targetUserCd) === -1) {
                    targetIdList.push(targetUserCd);
                    targetUserObjList.push(user);
                }
            });
```

### 最後に注意点
本件はあくまでも奥の手です。本当にこの内容で対応を実施すべきかどうかを熟考した上で適用すべきと考えます。
申し訳ありませんが、この対応によって発生した障害等について、一切責任を負いませんので、ご了承ください。