- CodeParser: normalize scanned barcode to uppercase and trim whitespace to handle scanner hardware outputting lowercase or trailing characters - RegistrationPage: swap layout so location field is above zongpai field - Lock mode: zongpai display changes to scrollable list supporting multiple entries with swipe-to-delete and per-item delete buttons - Lock mode: batch submit when multiple zongpai numbers are queued - Show scanned barcode content in invalid code error messages Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
42 lines
1.2 KiB
Dart
42 lines
1.2 KiB
Dart
// lib/services/code_parser.dart
|
|
class CodeParser {
|
|
static final _zongpaiRegex = RegExp(
|
|
r'^\d{2}(B|C|T)\d+$|^\d{2}(BW|CW)\d{4}$',
|
|
);
|
|
static final _locationRegex = RegExp(
|
|
r'^[A-Z0-9]+-[A-Z0-9]+-[A-Z0-9]+$',
|
|
);
|
|
static final _transitRegex = RegExp(
|
|
r'^TRANS-',
|
|
);
|
|
|
|
static ParseResult parse(String code) {
|
|
final trimmed = code.trim();
|
|
if (trimmed.isEmpty) {
|
|
return ParseResult(type: CodeType.invalid, value: code);
|
|
}
|
|
final normalized = trimmed.toUpperCase();
|
|
if (_transitRegex.hasMatch(normalized)) {
|
|
return ParseResult(type: CodeType.locationTransit, value: normalized);
|
|
}
|
|
if (_zongpaiRegex.hasMatch(normalized)) {
|
|
return ParseResult(type: CodeType.zongpaiNo, value: normalized);
|
|
}
|
|
if (_locationRegex.hasMatch(normalized)) {
|
|
return ParseResult(type: CodeType.locationNormal, value: normalized);
|
|
}
|
|
return ParseResult(type: CodeType.invalid, value: code);
|
|
}
|
|
|
|
static bool isLocation(CodeType type) =>
|
|
type == CodeType.locationNormal || type == CodeType.locationTransit;
|
|
}
|
|
|
|
enum CodeType { zongpaiNo, locationNormal, locationTransit, invalid }
|
|
|
|
class ParseResult {
|
|
final CodeType type;
|
|
final String value;
|
|
ParseResult({required this.type, required this.value});
|
|
}
|