1. 概述
1.1 問題描述
在使用多個複選按鈕元件的時候,如何實現全選和批量操作的功能呢?效果如下圖所示:
1.2 實現思路
根據元件名獲取元件陣列,遍歷指派來實現全選。根據元件狀態,批量獲取選中元件並執行相關操作。API說明可以參考:API匯總
注1:本文方案僅支援填報預覽下使用 。
注2:本方案行動端僅支援批量修改,批量刪除方案請參考:[通用]JS行動端實現批量刪除 。
2. 範例
2.1 準備資料
建立普通報表,建立資料庫查詢資料集 ds1,SQL 語句為:SELECT * FROM Sales
2.2 設計表格
如下圖設計填報範本的表格樣式,其中 A3 儲存格的左父格為 B3。
A2、A3 儲存格中新增「複選按鈕元件」,C1、D1、E1、F1、G1、C3、D3、E3、F3、G3 儲存格中新增「正文元件」,H5 儲存格新增按鈕元件。
給A3的複選按鈕元件設定元件名稱:box。該名稱可自訂,但如果修改了此名稱,後續 JS 程式碼中的元件名稱 box 也需要同步修改。
2.3 全選功能實現
1)選中 A2 儲存格(全選複選框),新增一個狀態改變事件,如下圖所示:
JavaScript 程式碼如下:
注:程式碼中預設為第一個 sheet ,其他 sheet 需要修改 _g().setCellValue() API的 sheet 參數,可參考:獲取和設定儲存格值API
var flag = this.getValue();
//獲取當前值
var boxes = _g().getWidgetsByName("box");
//獲取當前頁的複選按鈕元件陣列
if (typeof(boxes[0]) != "undefined") {
for (i = 0; i < boxes.length; i ) {
var cr=FR.cellStr2ColumnRow(boxes[i].options.location);
//獲取行列號物件
_g().setCellValue(0,cr.col,cr.row,flag);
//如果元件大於1個,則遍歷指派
}
} else {
var cr=FR.cellStr2ColumnRow(boxes.options.location);
//獲取行列號物件
_g().setCellValue(0,cr.col,cr.row,flag);
//如果元件只有1個,則直接指派
}
如果jar包版本在11.0.6(2022-06-30)及之後,可使用效能更好的批量指派API來實現此功能。API說明可以參考:複選按鈕元件專有
注:該API不支援行動端。
JavaScript 程式碼如下:
var flag = this.getValue();
//獲取當前值
var boxes = _g().getWidgetsByName("box");
//獲取當前頁的複選按鈕元件陣列
if (typeof(boxes[0]) != "undefined") {
var configs = [];
for (i = 0; i < boxes.length; i++) {
var cr=FR.cellStr2ColumnRow(boxes[i].options.location);
//獲取行列號物件
configs.push({reportIndex:0,col:cr.col,row:cr.row,value:flag});
//如果元件大於1個,則遍曆將行列號以及值資訊插入陣列中
}
_g().setCellsQuick(configs);
//批量指派
//如果範本存在凍結,且被指派儲存格的行高列寬會改變,則需要更換此句為:_g().setCellsValueInBatch(configs);
} else {
var cr=FR.cellStr2ColumnRow(boxes.options.location);
//獲取行列號物件
_g().setCellValue(0,cr.col,cr.row,flag);
//如果元件只有1個,則直接指派
}
2)選中 A3 儲存格(單選複選框),新增一個狀態改變事件,如下圖所示:
JavaScript 程式碼如下:
注:程式碼中預設為第一個 sheet ,其他 sheet 需要修改 _g().setCellValue() API的 sheet 參數,可參考:獲取和設定儲存格值API
var isAllChecked = true;
//設標度記狀態為選中
var boxes = _g().getWidgetsByName("box");
//獲取當前頁的複選按鈕元件陣列
if (typeof(boxes[0]) != "undefined") {
for (i = 0; i < boxes.length; i ) {
isAllChecked = boxes[i].getValue() == true ? isAllChecked : false;
//如果元件大於1個,則遍歷獲取值,一旦出現未選中狀態的按鈕,則將標記值改為false
}
} else {
isAllChecked = boxes.getValue();
//如果元件只有1個,則直接獲取元件值,並傳給標記值
}
_g().setCellValue(0, 0, 1, isAllChecked);
//將標記值賦給A2儲存格
2.4 批量刪除行功能實現
選中 H5 儲存格(按鈕元件),新增一個點選事件,如下圖所示:
JavaScript 程式碼如下:
注:以下 JS 程式碼不支援行動端。
var boxes = _g().getWidgetsByName("box");
//獲取當前頁的複選按鈕元件陣列
var cells = [];
if (typeof(boxes[0]) != "undefined") {
for (i = 0; i < boxes.length; i ) {
if (boxes[i].selected()) {
cells.push(boxes[i].options.location); //如果元件大於1個,則遍歷判斷是否選中,將選中的元件所在的儲存格編號塞進陣列中
}
}
} else {
if (boxes.selected()) {
cells.push(boxes.options.location);
//如果元件只有1個,則直接判斷是否選中,選中的話把儲存格編號塞進陣列中
}
}
_g().deleteRows(cells);
//根據儲存格編號刪除行
//_g().verifyAndWriteReport(true);
//執行校驗提交所有sheet,如有刪除行時直接提交的需求,可以啟用該句
2.5 批量修改功能實現
給C1、D1、E1、F1、G1儲存格的元件,新增編輯結束事件,如下圖所示:
JavaScript 程式碼如下:
注:程式碼中預設為第一個 sheet ,其他 sheet 需要修改 _g().setCellValue() API的 sheet 參數,可參考:獲取和設定儲存格值API
var boxes = _g().getWidgetsByName("box");
//獲取當前頁的複選按鈕元件陣列
var value = this.getValue();
//獲取當前元件值
if (typeof(boxes[0]) != "undefined") {
for (i = 0; i < boxes.length; i ) {
if (boxes[i].getValue() == true) {
var row = FR.cellStr2ColumnRow(boxes[i].options.location).row;
//獲取行號
var col = FR.cellStr2ColumnRow(this.options.location).col;
//獲取列號
_g().setCellValue(0, col, row, value);
//如果元件大於1個,則遍歷修改選中行當前列的值
}
}
} else {
if (boxes.getValue() == true) {
var row = FR.cellStr2ColumnRow(boxes.options.location).row;
//獲取行號
var col = FR.cellStr2ColumnRow(this.options.location).col;
//獲取列號
_g().setCellValue(0, col, row, value);
//如果元件只有1個,則直接判斷是否選中,選中的話修改當前列的值
}
}
如果 jar 包版本在 11.0.6(2022-06-30)及之後,可使用效能更好的批量指派API來實現此功能。API說明可以參考:複選按鈕元件專有
注:該API不支援行動端。
JavaScript 程式碼如下:
2.6 效果預覽
儲存範本,點選[填報預覽]。
PC 端
效果如1.1節所示
行動端
jar 包在 11.0.6 之前的效果如下所示:
注1:本方案僅支援行動端批量修改操作,不支援行動端批量刪除操作。
注2:當頁面資料量較大時,全選操作會導致頁面卡頓,此時可以考慮使用 填報分頁 來優化
3. 範本下載
點選下載範本:JS實現複選框元件全選和批量操作.cpt
jar包版本在11.0.6(2022-06-30)及之後,可選擇此版本,效能更好: