diff --git a/npm/src/components/Table.js b/npm/src/components/Table.js index 5404240..6eb7b8d 100644 --- a/npm/src/components/Table.js +++ b/npm/src/components/Table.js @@ -13,7 +13,8 @@ const Table = props => { const actionRef = useRef(); const modelRef = useRef(); - const [statJustify, setStatJustify] = useState('space-evenly'); + const [requestStatistic, setRequestStatistic] = useState({}); + const [statisticJustify, setStatisticJustify] = useState('space-evenly'); const statSize = useResizeDetector({ handleWidth: false, @@ -178,12 +179,13 @@ const Table = props => { danger={buttonValue.danger ?? undefined} size='small' onClick={(e) => { e.preventDefault(); buttonAction(buttonValue, record); }} - >{buttonValue.locale ? localeValue(buttonValue.title) : buttonValue.title} + children={buttonValue.locale ? localeValue(buttonValue.title) : buttonValue.title} + /> ); } } } - return buttons ? {buttons} : null; + return buttons ? : null; }; } @@ -275,16 +277,17 @@ const Table = props => { href={buttonHref(buttonValue)} danger={buttonValue.danger ?? undefined} onClick={(e) => { e.preventDefault(); buttonAction(buttonValue); }} - >{buttonValue.locale ? localeValue(buttonValue.title) : buttonValue.title}); + children={buttonValue.locale ? localeValue(buttonValue.title) : buttonValue.title} + />); } } useEffect(() => { if (statSize.height) { if (statSize.height > 100) { - setStatJustify('space-between'); + setStatisticJustify('start'); } else { - setStatJustify('space-evenly'); + setStatisticJustify('space-evenly'); } } }, [statSize.height]); @@ -303,12 +306,23 @@ const Table = props => { params._sort = sort[params._order]; } const result = await ajax(window.location.pathname + '?' + new URLSearchParams(params).toString()); - return (result && result.error === 0) ? { - success: true, - data: result.data.list, - total: result.data.count, - } : false; + if (result && result.error === 0) { + setRequestStatistic(result.data.statistic ?? {}); + return { + success: true, + data: result.data.list, + total: result.data.count, + }; + } else { + setRequestStatistic({}); + return { + success: false, + data: [], + total: 0, + }; + } }} + revalidateOnFocus={false} rowKey='id' search={tableSearch ? { labelWidth: 'auto' } : false} pagination={{ @@ -332,45 +346,102 @@ const Table = props => { href={buttonHref(buttonValue, selectedRowKeys)} danger={buttonValue.danger ?? undefined} onClick={(e) => { e.preventDefault(); buttonAction(buttonValue, selectedRowKeys); }} - >{buttonValue.locale ? localeValue(buttonValue.title) : buttonValue.title} + children={buttonValue.locale ? localeValue(buttonValue.title) : buttonValue.title} + /> ); } } - return {buttons}; + return ; }} - columnsState={{ - persistenceKey: window.location.pathname, - persistenceType: 'sessionStorage', + options={{ + setting: false }} + summary={notEmpty(global.config.summary) ? pageData => { + let sumVisible = false; + let avgVisible = false; + let sumCells = []; + let avgCells = []; + + if (notEmpty(columns) && notEmpty(pageData)) { + let titleIndex = '0'; + let summaryColumns = []; + + if (notEmpty(global.config.batch.button)) { + titleIndex = '1'; + summaryColumns.push('_batch') + } + for (const column of Object.values(columns)) { + summaryColumns.push(column.dataIndex) + } + + for (const [index, key] of Object.entries(summaryColumns)) { + if (global.config.summary[key]) { + let precision = global.config.summary[key].precision ?? 2; + let sum = pageData.reduce((pre, cur) => +cur[key] + pre, 0); + let result = sum.toFixed(precision); + sumVisible = true; + sumCells.push( + + {index === titleIndex ? <>{result} : result} + + ); + if (global.config.summary[key].type === 'sum') { + avgCells.push( + + {index === titleIndex ? : undefined} + + ); + } else { + avgVisible = true; + result = (sum / pageData.length).toFixed(precision); + avgCells.push( + + {index === titleIndex ? <>{result} : result} + + ); + } + } else { + sumCells.push( + + {index === titleIndex ? : undefined} + + ); + avgCells.push( + + {index === titleIndex ? : undefined} + + ); + } + } + } + + return sumVisible || avgVisible ? ( + + {sumVisible ? () : undefined} + {avgVisible ? () : undefined} + + ) : undefined; + } : undefined} tableExtraRender={notEmpty(global.config.statistic) ? (_, pageData) => { const statistic = []; - for (const value of Object.values(global.config.statistic)) { - let result = pageData.reduce((pre, cur) => +cur[value.key] + pre, 0); - if (value.type === 'avg') { - result = result / pageData.length; + for (const [key, value] of Object.entries(global.config.statistic)) { + let statValue = value.value ?? undefined; + if (notEmpty(requestStatistic)) { + statValue = requestStatistic[key] ?? statValue; } - let columnTitle = localeValue(global.config.column[value.key].title); - let statisticTitle = localeValue(value.title).replace('{{field}}', columnTitle); statistic.push( -1) ? value.precision : undefined} - prefix={(value.prefix) ?? undefined} - suffix={(value.suffix) ?? undefined} - groupSeparator={(value.thousandsSeparator) ?? undefined} - decimalSeparator={(value.decimalSeparator) ?? undefined} + style={{ textAlign: 'center' }} + title={value.title} + value={statValue} /> ); } return ( - - {statistic} - + ); } : undefined} diff --git a/npm/src/locale/en_US.js b/npm/src/locale/en_US.js index d41af53..afe9e8e 100644 --- a/npm/src/locale/en_US.js +++ b/npm/src/locale/en_US.js @@ -41,8 +41,8 @@ const i18n = { ':success': 'Success', ':confirm_password': 'Confirm password', ':confirm_field': 'Different from {{field}}', - ':sum': 'Sum of {{field}}', - ':avg': 'Avg of {{field}}', + ':sum': 'Sum', + ':avg': 'Avg', ':upload_failed': 'Upload failed', }; diff --git a/npm/src/locale/zh_CN.js b/npm/src/locale/zh_CN.js index 650697d..3646f7b 100644 --- a/npm/src/locale/zh_CN.js +++ b/npm/src/locale/zh_CN.js @@ -41,8 +41,8 @@ const i18n = { ':success': '操作成功', ':confirm_password': '确认密码', ':confirm_field': '与{{field}}不一致', - ':sum': '{{field}}合计', - ':avg': '{{field}}平均', + ':sum': '合计', + ':avg': '平均', ':upload_failed': '上传失败', }; diff --git a/src/Admin/Form.php b/src/Admin/Form.php index d19919e..20d4f5f 100755 --- a/src/Admin/Form.php +++ b/src/Admin/Form.php @@ -154,7 +154,7 @@ public static function render(string $table, ?callable $middleware = null) $cache->delete($table . '_enum_list'); if (is_callable($middleware)) { - $middleware('return', $rsId); + $middleware('api', $rsId); } Model::userLog($userId, true); diff --git a/src/Admin/Table.php b/src/Admin/Table.php index ee76f1a..6cc2cad 100755 --- a/src/Admin/Table.php +++ b/src/Admin/Table.php @@ -27,7 +27,6 @@ class Table { public static array $config = []; private static int $buttonIndex = 0; - private static int $statisticIndex = 0; /** * Create a colum @@ -68,22 +67,35 @@ public static function button(string $form): TableButton return new TableButton(self::$buttonIndex); } + /** + * Create a column summary + * + * @param string $key + * @return TableSummary + */ + public static function summary(string $key): TableSummary + { + self::$config[__FUNCTION__][$key] = [ + 'type' => 'sum', + ]; + + return new TableSummary($key); + } + /** * Create a statistic * * @param string $key - * @return TableStatistic + * @return TableStatistic */ public static function statistic(string $key): TableStatistic { - ++self::$statisticIndex; - self::$config[__FUNCTION__][self::$statisticIndex] = [ + self::$config[__FUNCTION__][$key] = [ 'key' => $key, - 'title' => ':sum', - 'type' => 'sum', + 'title' => $key, ]; - return new TableStatistic(self::$statisticIndex); + return new TableStatistic($key); } /** @@ -100,16 +112,6 @@ public static function statistic(string $key): TableStatistic */ public static function render(string $table, ?callable $middleware = null) { - - $page = (int) (Request::$data['current'] ?? 1); - $limit = (int) (Request::$data['pageSize'] ?? 20); - $limit = $limit < 100 ? $limit : 100; - $order = trim(Request::$data['_order'] ?? '') ?: 'id'; - $sort = trim(Request::$data['_sort'] ?? '') ?: 'asc'; - - $sortLimit = ['ascend' => 'asc', 'descend' => 'desc']; - $sort = $sortLimit[$sort] ?? 'asc'; - $userId = Auth::getUserId(); $userInfo = Model::getUserInfo($userId); @@ -156,11 +158,11 @@ public static function render(string $table, ?callable $middleware = null) } } - $statistic = []; - if (isset(Table::$config['statistic'])) { - foreach (Table::$config['statistic'] as $v) { - if (isset($column[$v['key']])) { - $statistic[] = $v; + $summary = []; + if (isset(Table::$config['summary'])) { + foreach (Table::$config['summary'] as $k => $v) { + if (isset($column[$k])) { + $summary[$k] = $v; } } } @@ -169,7 +171,8 @@ public static function render(string $table, ?callable $middleware = null) 'column' => $column, 'toolbar' => $toolbar, 'batch' => $batch, - 'statistic' => $statistic, + 'summary' => $summary, + 'statistic' => Table::$config['statistic'] ?? [], ]; if (is_callable($middleware)) { @@ -180,6 +183,15 @@ public static function render(string $table, ?callable $middleware = null) Response::render('public/alight-admin/index.html', ['title' => Request::$data['_title'] ?? '', 'script' => Admin::globalScript('Table', $renderData)]); } else { + $page = (int) (Request::$data['current'] ?? 1); + $limit = (int) (Request::$data['pageSize'] ?? 20); + $limit = $limit < 100 ? $limit : 100; + $order = trim(Request::$data['_order'] ?? '') ?: 'id'; + $sort = trim(Request::$data['_sort'] ?? '') ?: 'asc'; + + $sortLimit = ['ascend' => 'asc', 'descend' => 'desc']; + $sort = $sortLimit[$sort] ?? 'asc'; + $column = []; if (isset(Table::$config['column'])) { foreach (Table::$config['column'] as $k => $v) { @@ -210,7 +222,7 @@ public static function render(string $table, ?callable $middleware = null) ]; if (is_callable($middleware)) { - $middleware('return', $resData); + $middleware('api', $resData); } Response::api(0, $resData); diff --git a/src/Admin/TableStatistic.php b/src/Admin/TableStatistic.php index cfb0a22..450a537 100644 --- a/src/Admin/TableStatistic.php +++ b/src/Admin/TableStatistic.php @@ -15,17 +15,17 @@ class TableStatistic { - private int $index = 0; + private string $key; /** * Define the configuration index * - * @param int $index + * @param string $key * @return TableStatistic */ - public function __construct(int $index) + public function __construct(string $key) { - $this->index = $index; + $this->key = $key; return $this; } @@ -37,71 +37,19 @@ public function __construct(int $index) */ public function title(string $value): TableStatistic { - Table::$config['statistic'][$this->index][__FUNCTION__] = $value; + Table::$config['statistic'][$this->key][__FUNCTION__] = $value; return $this; } /** - * Set average value + * Set value * + * @param mixed $value * @return TableStatistic */ - public function avg(): TableStatistic + public function value($value): TableStatistic { - Table::$config['statistic'][$this->index]['type'] = __FUNCTION__; - if (Table::$config['statistic'][$this->index]['title'] == ':sum') { - Table::$config['statistic'][$this->index]['title'] = ':avg'; - } - return $this; - } - - /** - * Set precision - * - * @param int $number - * @return TableStatistic - */ - public function precision(int $number): TableStatistic - { - Table::$config['statistic'][$this->index][__FUNCTION__] = $number; - return $this; - } - - /** - * Set value prefix - * - * @param string $value - * @return TableStatistic - */ - public function prefix(string $value): TableStatistic - { - Table::$config['statistic'][$this->index][__FUNCTION__] = $value; - return $this; - } - - /** - * Set value suffix - * - * @param string $value - * @return TableStatistic - */ - public function suffix(string $value): TableStatistic - { - Table::$config['statistic'][$this->index][__FUNCTION__] = $value; - return $this; - } - - /** - * Set separator - * - * @param string $thousands - * @param string $decimal - * @return TableStatistic - */ - public function separator(string $thousands = ',', string $decimal = '.'): TableStatistic - { - Table::$config['statistic'][$this->index]['thousandsSeparator'] = $thousands; - Table::$config['statistic'][$this->index]['decimalSeparator'] = $decimal; + Table::$config['statistic'][$this->key][__FUNCTION__] = $value; return $this; } } diff --git a/src/Admin/TableSummary.php b/src/Admin/TableSummary.php new file mode 100644 index 0000000..011b9d8 --- /dev/null +++ b/src/Admin/TableSummary.php @@ -0,0 +1,54 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Alight\Admin; + +class TableSummary +{ + private string $key; + + /** + * Define the configuration index + * + * @param string $key + * @return TableSummary + */ + public function __construct(string $key) + { + $this->key = $key; + return $this; + } + + /** + * Set average value + * + * @return TableSummary + */ + public function avg(): TableSummary + { + Table::$config['summary'][$this->key]['type'] = __FUNCTION__; + return $this; + } + + /** + * Set precision + * + * @param int $number + * @return TableSummary + */ + public function precision(int $number): TableSummary + { + Table::$config['summary'][$this->key][__FUNCTION__] = $number; + return $this; + } +}