feat(pagination): 공통 컨트롤 도입과 사용자 관리 가이드 추가

- 테이블 푸터에서 SuperportPaginationControls를 사용하도록 각 관리 페이지 페이지네이션 로직을 정리

- SuperportPaginationControls 위젯을 추가하고 SuperportTable 푸터를 개선해 페이지 사이즈 선택과 이동 버튼을 분리

- 사용자 등록·계정 관리 요구사항을 문서화한 doc/user_setting.md를 작성하고 AGENTS.md 코멘트 규칙을 업데이트

- flutter analyze를 수행해 빌드 경고가 없음을 확인
This commit is contained in:
JiWoong Sul
2025-10-24 16:24:02 +09:00
parent 9d6cbb1ab2
commit 9beb161527
17 changed files with 432 additions and 502 deletions

View File

@@ -522,36 +522,45 @@ class _RentalPageState extends State<RentalPage> {
: '대여 데이터가 없습니다.',
description: _errorMessage ?? '검색 조건을 조정해 다시 시도하세요.',
)
: ShadTable.list(
header: RentalTableSpec.headers
.map(
(header) =>
ShadTableCell.header(child: Text(header)),
)
.toList(),
children: [
for (final record in visibleRecords)
_buildRecordRow(record).map(
(value) => ShadTableCell(
child: Text(
value,
overflow: TextOverflow.ellipsis,
: () {
final baseOffset = _rowNumberOffset(
visibleRecords.length,
);
return ShadTable.list(
header: RentalTableSpec.headers
.map(
(header) =>
ShadTableCell.header(child: Text(header)),
)
.toList(),
children: [
for (var i = 0; i < visibleRecords.length; i++)
_buildRecordRow(
visibleRecords[i],
baseOffset + i + 1,
).map(
(value) => ShadTableCell(
child: Text(
value,
overflow: TextOverflow.ellipsis,
),
),
),
),
],
columnSpanExtent: (index) =>
const FixedTableSpanExtent(
RentalTableSpec.columnSpanWidth,
),
rowSpanExtent: (index) => const FixedTableSpanExtent(
RentalTableSpec.rowSpanHeight,
),
onRowTap: (rowIndex) {
final record = visibleRecords[rowIndex];
_selectRecord(record, openDetail: true);
},
),
],
columnSpanExtent: (index) =>
const FixedTableSpanExtent(
RentalTableSpec.columnSpanWidth,
),
rowSpanExtent: (index) =>
const FixedTableSpanExtent(
RentalTableSpec.rowSpanHeight,
),
onRowTap: (rowIndex) {
final record = visibleRecords[rowIndex];
_selectRecord(record, openDetail: true);
},
);
}(),
),
if (filtered.isNotEmpty) ...[
const SizedBox(height: 12),
@@ -747,9 +756,9 @@ class _RentalPageState extends State<RentalPage> {
}
}
List<String> _buildRecordRow(RentalRecord record) {
List<String> _buildRecordRow(RentalRecord record, int displayIndex) {
return [
record.number.split('-').last,
displayIndex.toString(),
_dateFormatter.format(record.processedAt),
record.warehouse,
record.rentalType,
@@ -765,6 +774,16 @@ class _RentalPageState extends State<RentalPage> {
];
}
int _rowNumberOffset(int currentCount) {
final page = _result?.page ?? _currentPage;
final pageSize = _result?.pageSize ?? _pageSize;
final safePage = page > 0 ? page : 1;
final safePageSize = pageSize > 0
? pageSize
: (currentCount > 0 ? currentCount : 1);
return (safePage - 1) * safePageSize;
}
Future<void> _showDetailDialog(RentalRecord record) async {
await showInventoryTransactionDetailDialog<void>(
context: context,