feat: 公开商品页重设计 + web 上传修复 + 二维码配置
- 公开商品页(/product/:uuid)全面重设计:全宽正方形图片轮播、 左右滑动切图、点击放大全屏查看、商品参数含描述、页脚贴底 - 修复 Flutter web 文件上传无反应(path→bytes) - 修复 web 路由空白页(usePathUrlStrategy + 单层 MaterialApp.router) - 二维码 URL 改为从 STORAGE_PUBLIC_URL 环境变量读取 - 新增 PUBLIC_URL dart-define → AppConfig.publicBaseUrl - 新增 CI/CD workflows + NAS runner compose 配置 - seed S001 补充商品描述字段 Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -1,5 +1,6 @@
|
||||
import 'dart:typed_data';
|
||||
import 'package:file_picker/file_picker.dart';
|
||||
import 'package:flutter/foundation.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter/services.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
@@ -91,16 +92,20 @@ class _ProductDetailScreenState extends ConsumerState<ProductDetailScreen> {
|
||||
final result = await FilePicker.platform.pickFiles(
|
||||
type: FileType.image,
|
||||
allowMultiple: false,
|
||||
withData: true,
|
||||
);
|
||||
if (result == null || result.files.isEmpty) return;
|
||||
final path = result.files.first.path;
|
||||
if (path == null) return;
|
||||
final file = result.files.first;
|
||||
final String? filePath = kIsWeb ? null : file.path;
|
||||
final fileBytes = file.bytes;
|
||||
if (filePath == null && fileBytes == null) return;
|
||||
|
||||
setState(() => _uploading = true);
|
||||
try {
|
||||
final img = await ref
|
||||
.read(productRepositoryProvider)
|
||||
.uploadImage(_product!.id, path);
|
||||
.uploadImage(_product!.id, filePath,
|
||||
bytes: fileBytes, fileName: file.name);
|
||||
_updateImages([..._product!.images, img]);
|
||||
if (mounted) {
|
||||
ScaffoldMessenger.of(context).showSnackBar(
|
||||
@@ -357,7 +362,7 @@ class _ProductDetailScreenState extends ConsumerState<ProductDetailScreen> {
|
||||
}
|
||||
|
||||
Widget _buildPublicLinkSection(Product p) {
|
||||
final publicUrl = 'https://jiu.51yanmei.com/product/${p.publicId}';
|
||||
final publicUrl = '${AppConfig.publicBaseUrl}/product/${p.publicId}';
|
||||
return Card(
|
||||
elevation: 0,
|
||||
shape: RoundedRectangleBorder(
|
||||
|
||||
Reference in New Issue
Block a user