Browse Source

对比展示逻辑优化前

master
hejl 2 months ago
parent
commit
5f679197e5
  1. 113
      win_text_editor/lib/modules/data_compare/controllers/data_compare_controller.dart
  2. 85
      win_text_editor/lib/modules/data_compare/widgets/data_compare_data_source.dart
  3. 6
      win_text_editor/lib/modules/data_compare/widgets/data_compare_grid.dart
  4. 9
      win_text_editor/lib/modules/data_compare/widgets/data_compare_view.dart

113
win_text_editor/lib/modules/data_compare/controllers/data_compare_controller.dart

@ -8,11 +8,9 @@ class DataCompareController extends BaseContentController { @@ -8,11 +8,9 @@ class DataCompareController extends BaseContentController {
List<String> rightColumns = [];
List<Map<String, dynamic>> leftData = [];
List<Map<String, dynamic>> rightData = [];
late DataCompareDataSource dataSource;
DataCompareController() {
dataSource = DataCompareDataSource(this);
}
//
List<Map<String, dynamic>> comparedData = [];
Future<void> importCsv(bool isLeftTable, String csvContent) async {
try {
@ -31,19 +29,17 @@ class DataCompareController extends BaseContentController { @@ -31,19 +29,17 @@ class DataCompareController extends BaseContentController {
if (lines[i].trim().isEmpty) continue;
final values = lines[i].split(delimiter);
if (values.length < 1) continue;
if (values.isEmpty) continue;
//
final row = {
'serial': i.toString(), //
'key': values[0], //
'serial': i.toString(),
'key': values[0],
...Map.fromIterables(
headers,
List.generate(headers.length, (j) => j + 1 < values.length ? values[j + 1] : ''),
),
};
//
for (int j = 0; j < headers.length; j++) {
row[headers[j]] = (j + 1 < values.length) ? values[j + 1] : '';
}
data.add(row);
}
@ -55,18 +51,61 @@ class DataCompareController extends BaseContentController { @@ -55,18 +51,61 @@ class DataCompareController extends BaseContentController {
rightData = data;
}
compareData();
_compareData();
notifyListeners();
} catch (e) {
Logger().error('${isLeftTable ? '左表' : '右表'}数据导入失败: $e');
Logger().error('${isLeftTable ? '左表' : '右表'}导入失败: $e');
rethrow;
}
}
void compareData() {
// Implement comparison logic here
// This would update the comparison status for each row
dataSource.updateData(leftData, rightData);
void _compareData() {
comparedData = [];
// 1.
if (leftData.isEmpty && rightData.isEmpty) return;
// 2.
if (leftData.isEmpty || rightData.isEmpty) {
final source = leftData.isEmpty ? rightData : leftData;
comparedData =
source
.map((row) => {...row, 'match_status': 'no_match', 'is_left': leftData.isNotEmpty})
.toList();
return;
}
// 3.
final rightMap = {for (var r in rightData) r['key']: r};
for (var leftRow in leftData) {
final rightRow = rightMap[leftRow['key']];
if (rightRow != null) {
bool isFullMatch = leftColumns.every((col) => leftRow[col] == rightRow[col]);
comparedData.add({
...leftRow,
'match_status': isFullMatch ? 'full_match' : 'key_match',
'is_left': true,
'right_data': rightRow,
});
rightMap.remove(leftRow['key']);
} else {
comparedData.add({...leftRow, 'match_status': 'no_match', 'is_left': true});
}
}
//
comparedData.addAll(
rightMap.values.map((row) => ({...row, 'match_status': 'no_match', 'is_left': false})),
);
// 4.
comparedData.sort((a, b) {
const order = {'full_match': 0, 'key_match': 1, 'no_match': 2};
return order[a['match_status']]!.compareTo(order[b['match_status']]!);
});
}
void exportLeftTable(String matchType) {
@ -89,39 +128,3 @@ class DataCompareController extends BaseContentController { @@ -89,39 +128,3 @@ class DataCompareController extends BaseContentController {
// TODO: implement onOpenFolder
}
}
class DataCompareDataSource extends DataGridSource {
final DataCompareController controller;
List<DataGridRow> _rows = [];
DataCompareDataSource(this.controller) {
_rows = [];
}
void updateData(List<Map<String, dynamic>> leftData, List<Map<String, dynamic>> rightData) {
_rows = [];
// Implement logic to combine left and right data into rows
// and determine comparison status
notifyListeners();
}
@override
List<DataGridRow> get rows => _rows;
@override
DataGridRowAdapter? buildRow(DataGridRow row) {
return DataGridRowAdapter(
cells:
row.getCells().map<Widget>((dataGridCell) {
return Container(
alignment: Alignment.center,
padding: EdgeInsets.all(8),
child:
dataGridCell.value.runtimeType == Icon
? dataGridCell.value
: Text(dataGridCell.value.toString()),
);
}).toList(),
);
}
}

85
win_text_editor/lib/modules/data_compare/widgets/data_compare_data_source.dart

@ -0,0 +1,85 @@ @@ -0,0 +1,85 @@
import 'package:flutter/material.dart';
import 'package:syncfusion_flutter_datagrid/datagrid.dart';
import 'package:win_text_editor/modules/data_compare/controllers/data_compare_controller.dart';
class DataCompareDataSource extends DataGridSource {
final DataCompareController controller;
DataCompareDataSource(this.controller) {
controller.addListener(_handleDataChange);
}
void _handleDataChange() {
notifyListeners();
}
@override
void dispose() {
controller.removeListener(_handleDataChange);
super.dispose();
}
@override
List<DataGridRow> get rows {
return controller.comparedData.map((row) {
final isLeft = row['is_left'] as bool;
final rightData = row['right_data'] as Map<String, dynamic>?;
final status = row['match_status'] as String;
return DataGridRow(
cells: [
//
DataGridCell<String>(columnName: 'left_serial', value: isLeft ? row['serial'] : ''),
DataGridCell<String>(columnName: 'left_key', value: isLeft ? row['key'] : ''),
...controller.leftColumns.map(
(col) => DataGridCell<String>(columnName: 'left_$col', value: isLeft ? row[col] : ''),
),
//
DataGridCell<Icon>(columnName: 'comparison', value: _getStatusIcon(status)),
//
DataGridCell<String>(
columnName: 'right_serial',
value: rightData?['serial'] ?? (!isLeft ? row['serial'] : ''),
),
DataGridCell<String>(
columnName: 'right_key',
value: rightData?['key'] ?? (!isLeft ? row['key'] : ''),
),
...controller.rightColumns.map(
(col) => DataGridCell<String>(
columnName: 'right_$col',
value: rightData?[col] ?? (!isLeft ? row[col] : ''),
),
),
],
);
}).toList();
}
Icon _getStatusIcon(String status) {
switch (status) {
case 'full_match':
return const Icon(Icons.double_arrow, color: Colors.green);
case 'key_match':
return const Icon(Icons.arrow_forward_ios, color: Colors.blue);
default:
return const Icon(Icons.close, color: Colors.red);
}
}
@override
DataGridRowAdapter? buildRow(DataGridRow row) {
return DataGridRowAdapter(
cells:
row.getCells().map<Widget>((cell) {
return Container(
alignment: Alignment.center,
padding: const EdgeInsets.all(8),
child: cell.value.runtimeType == Icon ? cell.value : Text(cell.value.toString()),
);
}).toList(),
);
}
}

6
win_text_editor/lib/modules/data_compare/widgets/data_compare_grid.dart

@ -5,7 +5,9 @@ import 'package:win_text_editor/modules/data_compare/controllers/data_compare_co @@ -5,7 +5,9 @@ import 'package:win_text_editor/modules/data_compare/controllers/data_compare_co
class DataCompareGrid extends StatelessWidget {
final DataCompareController controller;
const DataCompareGrid({super.key, required this.controller});
final DataGridSource dataSource;
const DataCompareGrid({super.key, required this.dataSource, required this.controller});
@override
Widget build(BuildContext context) {
@ -14,7 +16,7 @@ class DataCompareGrid extends StatelessWidget { @@ -14,7 +16,7 @@ class DataCompareGrid extends StatelessWidget {
borderRadius: BorderRadius.circular(2.0), //
),
child: SfDataGrid(
source: controller.dataSource,
source: dataSource,
columns: _buildColumns(),
stackedHeaderRows: _buildStackedHeaders(),
columnWidthMode: ColumnWidthMode.fill,

9
win_text_editor/lib/modules/data_compare/widgets/data_compare_view.dart

@ -2,12 +2,12 @@ import 'dart:io'; @@ -2,12 +2,12 @@ import 'dart:io';
import 'package:file_picker/file_picker.dart';
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:provider/provider.dart';
import 'package:syncfusion_flutter_datagrid/datagrid.dart';
import 'package:win_text_editor/framework/controllers/logger.dart';
import 'package:win_text_editor/framework/controllers/tab_items_controller.dart';
import 'package:win_text_editor/modules/data_compare/controllers/data_compare_controller.dart';
import 'package:win_text_editor/modules/data_compare/widgets/data_compare_data_source.dart';
import 'data_compare_grid.dart'; //
class DataCompareView extends StatefulWidget {
@ -23,6 +23,8 @@ class _DataCompareViewState extends State<DataCompareView> { @@ -23,6 +23,8 @@ class _DataCompareViewState extends State<DataCompareView> {
late final DataGridController _dataGridController;
bool _isControllerFromTabManager = false;
late final DataCompareDataSource _dataSource;
get tabManager => Provider.of<TabItemsController>(context, listen: false);
@override
@ -39,6 +41,9 @@ class _DataCompareViewState extends State<DataCompareView> { @@ -39,6 +41,9 @@ class _DataCompareViewState extends State<DataCompareView> {
_isControllerFromTabManager = false;
tabManager.registerController(widget.tabId, _controller);
}
// DataSource
_dataSource = DataCompareDataSource(_controller);
}
@override
@ -208,7 +213,7 @@ class _DataCompareViewState extends State<DataCompareView> { @@ -208,7 +213,7 @@ class _DataCompareViewState extends State<DataCompareView> {
],
),
),
Expanded(child: DataCompareGrid(controller: controller)),
Expanded(child: DataCompareGrid(dataSource: _dataSource, controller: controller)),
],
),
);

Loading…
Cancel
Save