diff --git a/client/lib/models/product.dart b/client/lib/models/product.dart index efb56d6..d5fa561 100644 --- a/client/lib/models/product.dart +++ b/client/lib/models/product.dart @@ -14,6 +14,8 @@ class Product { final double? purchasePrice; final double? salePrice; final int? minStock; + // 生产日期(YYYY-MM-DD,后端 Date 序列化,空串=未填) + final String? productionDate; final String? description; final String? remark; final Map? customFields; @@ -41,6 +43,7 @@ class Product { this.purchasePrice, this.salePrice, this.minStock, + this.productionDate, this.description, this.remark, this.customFields, @@ -75,6 +78,7 @@ class Product { minStock: json['min_stock'] != null ? (json['min_stock'] as num).toInt() : null, + productionDate: json['production_date'] as String?, description: json['description'] as String?, remark: json['remark'] as String?, customFields: json['custom_fields'] as Map?, diff --git a/client/lib/screens/inventory/inventory_list_screen.dart b/client/lib/screens/inventory/inventory_list_screen.dart index df8160e..56cd0bd 100644 --- a/client/lib/screens/inventory/inventory_list_screen.dart +++ b/client/lib/screens/inventory/inventory_list_screen.dart @@ -613,6 +613,8 @@ class _InventoryListScreenState extends ConsumerState { return MCard( onTap: item.productId != null ? () => _openEditor(item) : null, nm: item.productName.isEmpty ? '-' : item.productName, + // 生产日期小字缀在品名后(原型 .mc-date,2026-07-10 用户口径) + nmSuffix: (item.productionDate ?? '').isEmpty ? null : item.productionDate, sub: sub.isEmpty ? null : sub, badges: [DsTextIconBadge(status)], amtWidget: Text.rich( diff --git a/client/lib/widgets/ds/m_card.dart b/client/lib/widgets/ds/m_card.dart index 935b7ed..0724b8b 100644 --- a/client/lib/widgets/ds/m_card.dart +++ b/client/lib/widgets/ds/m_card.dart @@ -101,6 +101,9 @@ class MCard extends StatelessWidget { /// mc-nm 标题(600 heading)。 final String nm; + /// mc-date 标题后缀(原型 .mc-nm .mc-date:xs muted mono,左距 8);null 不渲染。 + final String? nmSuffix; + /// mc-sub 副行(xs muted mono);null 不渲染。 final String? sub; @@ -119,6 +122,7 @@ class MCard extends StatelessWidget { const MCard({ super.key, required this.nm, + this.nmSuffix, this.sub, this.badges = const [], this.amt, @@ -151,13 +155,32 @@ class MCard extends StatelessWidget { child: Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ - Text(nm, - maxLines: 1, - overflow: TextOverflow.ellipsis, - style: TextStyle( - fontSize: AppDims.fsBody, - fontWeight: FontWeight.w600, - color: t.heading)), + Row( + mainAxisSize: MainAxisSize.min, + crossAxisAlignment: CrossAxisAlignment.baseline, + textBaseline: TextBaseline.alphabetic, + children: [ + Flexible( + child: Text(nm, + maxLines: 1, + overflow: TextOverflow.ellipsis, + style: TextStyle( + fontSize: AppDims.fsBody, + fontWeight: FontWeight.w600, + color: t.heading)), + ), + if (nmSuffix != null) ...[ + const SizedBox(width: 8), + Text(nmSuffix!, + style: TextStyle( + fontSize: AppDims.fsXs, + color: t.muted, + fontFamily: AppFonts.mono, + fontFamilyFallback: + AppFonts.monoFallback)), + ], + ], + ), if (sub != null) ...[ const SizedBox(height: 3), Text(sub!, diff --git a/client/lib/widgets/product_editor_drawer.dart b/client/lib/widgets/product_editor_drawer.dart index a8fc1eb..377248e 100644 --- a/client/lib/widgets/product_editor_drawer.dart +++ b/client/lib/widgets/product_editor_drawer.dart @@ -394,6 +394,9 @@ class _ProductEditorDrawerState extends ConsumerState<_ProductEditorDrawer> { if ((p.series ?? '').isNotEmpty) rows.add(('系列', b(p.series!))); if ((p.spec ?? '').isNotEmpty) rows.add(('规格', b(p.spec!))); if ((p.categoryName ?? '').isNotEmpty) rows.add(('分类', b(p.categoryName!))); + if ((p.productionDate ?? '').isNotEmpty) { + rows.add(('生产日期', b(p.productionDate!, mono: true))); + } if (widget.qty != null) { rows.add(( '当前库存', diff --git a/client/test/golden/goldens/inventory_list_mobile_a.png b/client/test/golden/goldens/inventory_list_mobile_a.png index 6b227a1..dacbcf7 100644 Binary files a/client/test/golden/goldens/inventory_list_mobile_a.png and b/client/test/golden/goldens/inventory_list_mobile_a.png differ diff --git a/client/test/golden/goldens/inventory_list_mobile_b.png b/client/test/golden/goldens/inventory_list_mobile_b.png index 4e9b5f2..b5ed808 100644 Binary files a/client/test/golden/goldens/inventory_list_mobile_b.png and b/client/test/golden/goldens/inventory_list_mobile_b.png differ diff --git a/client/test/golden/goldens/inventory_list_mobile_c.png b/client/test/golden/goldens/inventory_list_mobile_c.png index de587bc..1432458 100644 Binary files a/client/test/golden/goldens/inventory_list_mobile_c.png and b/client/test/golden/goldens/inventory_list_mobile_c.png differ diff --git a/client/test/golden/goldens/m_inventory_a.png b/client/test/golden/goldens/m_inventory_a.png index 226af52..21d3c9f 100644 Binary files a/client/test/golden/goldens/m_inventory_a.png and b/client/test/golden/goldens/m_inventory_a.png differ diff --git a/client/test/golden/goldens/m_inventory_b.png b/client/test/golden/goldens/m_inventory_b.png index cff175d..a0a4aed 100644 Binary files a/client/test/golden/goldens/m_inventory_b.png and b/client/test/golden/goldens/m_inventory_b.png differ diff --git a/client/test/golden/goldens/m_inventory_c.png b/client/test/golden/goldens/m_inventory_c.png index ecb4dea..8200a5d 100644 Binary files a/client/test/golden/goldens/m_inventory_c.png and b/client/test/golden/goldens/m_inventory_c.png differ diff --git a/design/prototype/index.html b/design/prototype/index.html index f0eea3f..987efee 100644 --- a/design/prototype/index.html +++ b/design/prototype/index.html @@ -437,7 +437,7 @@

移动专属组件 .m-*

来自 mobile-atoms.css 的移动专属原子,由 mobile-shell.js 装配外壳。复用上方公用原子(按钮/徽章/分段/输入),此处只展示移动新增的 .m-*

打开移动 UI Kit · 全部 .m-* 实机展示
-

移动壳 + 列表(实机预览)

.m-top · .m-tabbar · .m-page · .m-kpi · .m-search · .m-filters/.m-pill · .m-card/.m-row · .m-fab
+

移动壳 + 列表(实机预览)

.m-top · .m-tabbar · .m-page · .m-kpi · .m-search · .m-filters/.m-pill · .m-card/.m-row(.mc-nm 可带 .mc-date 日期后缀)· .m-fab