feat: inventory and inout info develop
This commit is contained in:
parent
fc0187acf0
commit
cf51cd8ada
|
@ -1,99 +0,0 @@
|
||||||
import 'dart:async';
|
|
||||||
import 'dart:io';
|
|
||||||
import 'package:dio/dio.dart';
|
|
||||||
import 'package:sk_base_mobile/constants/global_url.dart';
|
|
||||||
import 'package:sk_base_mobile/models/base_response.dart';
|
|
||||||
import 'package:sk_base_mobile/models/dict_type.model.dart';
|
|
||||||
import 'package:sk_base_mobile/services/dio.service.dart';
|
|
||||||
import '../constants/constants.dart';
|
|
||||||
|
|
||||||
// 登录
|
|
||||||
Future<Response> login(String username, String password) {
|
|
||||||
return DioService.dio.post(
|
|
||||||
Urls.login,
|
|
||||||
data: {'username': username, 'password': password},
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
// 获取个人信息
|
|
||||||
Future<Response> getUserInfo() {
|
|
||||||
return DioService.dio.get(
|
|
||||||
Urls.getUserInfo,
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
// 分页获取项目列表
|
|
||||||
Future<Response<PaginationData>> getProjects(Map params) {
|
|
||||||
return DioService.dio.get<PaginationData>(Urls.getProjects,
|
|
||||||
queryParameters: {'page': 1, 'pageSize': 10, ...params});
|
|
||||||
}
|
|
||||||
|
|
||||||
// 分页获取产品列表
|
|
||||||
Future<Response<PaginationData>> getProducts(Map params) {
|
|
||||||
return DioService.dio.get<PaginationData>(Urls.getProducts,
|
|
||||||
queryParameters: {'page': 1, 'pageSize': 10, ...params});
|
|
||||||
}
|
|
||||||
|
|
||||||
// 分页获取原材料出入库列表
|
|
||||||
Future<Response<PaginationData>> getInventoryInout(Map params) {
|
|
||||||
return DioService.dio.get<PaginationData>(Urls.inventoryInout,
|
|
||||||
queryParameters: {'page': 1, 'pageSize': 10, ...(params)});
|
|
||||||
}
|
|
||||||
|
|
||||||
// 创建出入库记录
|
|
||||||
Future<Response> createInventoryInout(Map params) {
|
|
||||||
return DioService.dio.post(Urls.inventoryInout, data: params);
|
|
||||||
}
|
|
||||||
|
|
||||||
// 更新出入库记录
|
|
||||||
Future<Response> updateInventoryInout(int id, Map params) {
|
|
||||||
return DioService.dio.put('${Urls.inventoryInout}/$id', data: params);
|
|
||||||
}
|
|
||||||
|
|
||||||
// 分页获取库存列表
|
|
||||||
Future<Response<PaginationData>> getInventory(Map params) {
|
|
||||||
return DioService.dio.get<PaginationData>(Urls.inventory,
|
|
||||||
queryParameters: {'page': 1, 'pageSize': 10, ...(params)});
|
|
||||||
}
|
|
||||||
|
|
||||||
// 一次性获取所有的字典类型(不分页)
|
|
||||||
Future<Response> getDictTypeAll(Map params) {
|
|
||||||
return DioService.dio.post(Urls.getDictType, data: params);
|
|
||||||
}
|
|
||||||
|
|
||||||
Future<Response> logout() {
|
|
||||||
return DioService.dio.post(
|
|
||||||
Urls.logout,
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
Future<Response> deleteAccount() {
|
|
||||||
return DioService.dio.post(
|
|
||||||
Urls.deleteAccount,
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
Future<Response> getAppConfig() {
|
|
||||||
Map<String, dynamic> query = {'ver': 0};
|
|
||||||
return DioService.dio.get(Urls.getAppConfig, queryParameters: query);
|
|
||||||
}
|
|
||||||
|
|
||||||
Future<Response> saveUserInfo(Map<String, dynamic> data) {
|
|
||||||
return DioService.dio.post(Urls.saveUserInfo, data: data);
|
|
||||||
}
|
|
||||||
|
|
||||||
Future<Response> uploadImg(File file,
|
|
||||||
{String? bussinessModule, String? bussinessRecordId}) async {
|
|
||||||
String fileName = file.path.split('/').last;
|
|
||||||
final filePath = await MultipartFile.fromFile(file.path, filename: fileName);
|
|
||||||
final formData = FormData.fromMap({
|
|
||||||
'bussinessRecordId': bussinessRecordId,
|
|
||||||
'bussinessModule': bussinessModule,
|
|
||||||
'file': filePath,
|
|
||||||
});
|
|
||||||
return DioService.dio.post(Urls.uploadAttachemnt, data: formData);
|
|
||||||
}
|
|
||||||
|
|
||||||
Future<Response> updateAvatar(String filename) {
|
|
||||||
return DioService.dio.post(Urls.updateAvatar, data: {'avatarPath': filename});
|
|
||||||
}
|
|
|
@ -0,0 +1,110 @@
|
||||||
|
import 'dart:async';
|
||||||
|
import 'dart:io';
|
||||||
|
import 'package:dio/dio.dart';
|
||||||
|
import 'package:sk_base_mobile/constants/global_url.dart';
|
||||||
|
import 'package:sk_base_mobile/models/base_response.dart';
|
||||||
|
import 'package:sk_base_mobile/models/dict_type.model.dart';
|
||||||
|
import 'package:sk_base_mobile/services/dio.service.dart';
|
||||||
|
import '../constants/constants.dart';
|
||||||
|
|
||||||
|
class Api {
|
||||||
|
// 登录
|
||||||
|
static Future<Response> login(String username, String password) {
|
||||||
|
return DioService.dio.post(
|
||||||
|
Urls.login,
|
||||||
|
data: {'username': username, 'password': password},
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
// 获取个人信息
|
||||||
|
static Future<Response> getUserInfo() {
|
||||||
|
return DioService.dio.get(
|
||||||
|
Urls.getUserInfo,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
// 分页获取项目列表
|
||||||
|
static Future<Response<PaginationData>> getProjects(Map params) {
|
||||||
|
return DioService.dio.get<PaginationData>(Urls.projects,
|
||||||
|
queryParameters: {'page': 1, 'pageSize': 10, ...params});
|
||||||
|
}
|
||||||
|
|
||||||
|
// 分页获取产品列表
|
||||||
|
static Future<Response<PaginationData>> getProducts(Map params) {
|
||||||
|
return DioService.dio.get<PaginationData>(Urls.products,
|
||||||
|
queryParameters: {'page': 1, 'pageSize': 10, ...params});
|
||||||
|
}
|
||||||
|
|
||||||
|
// 分页获取原材料出入库列表
|
||||||
|
static Future<Response<PaginationData>> getInventoryInout(Map params) {
|
||||||
|
return DioService.dio.get<PaginationData>(Urls.inventoryInout,
|
||||||
|
queryParameters: {'page': 1, 'pageSize': 10, ...(params)});
|
||||||
|
}
|
||||||
|
|
||||||
|
// 获取原材料出入库详情
|
||||||
|
static Future<Response> getInventoryInOutInfo(int id) {
|
||||||
|
return DioService.dio.get(
|
||||||
|
'${Urls.inventoryInout}/$id',
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
// 创建出入库记录
|
||||||
|
static Future<Response> createInventoryInout(Map params) {
|
||||||
|
return DioService.dio.post(Urls.inventoryInout, data: params);
|
||||||
|
}
|
||||||
|
|
||||||
|
// 更新出入库记录
|
||||||
|
static Future<Response> updateInventoryInout(int id, Map params) {
|
||||||
|
return DioService.dio.put('${Urls.inventoryInout}/$id', data: params);
|
||||||
|
}
|
||||||
|
|
||||||
|
// 分页获取库存列表
|
||||||
|
static Future<Response<PaginationData>> getInventory(Map params) {
|
||||||
|
return DioService.dio.get<PaginationData>(Urls.inventory,
|
||||||
|
queryParameters: {'page': 1, 'pageSize': 10, ...(params)});
|
||||||
|
}
|
||||||
|
|
||||||
|
// 一次性获取所有的字典类型(不分页)
|
||||||
|
static Future<Response> getDictTypeAll(Map params) {
|
||||||
|
return DioService.dio.post(Urls.getDictType, data: params);
|
||||||
|
}
|
||||||
|
|
||||||
|
static Future<Response> logout() {
|
||||||
|
return DioService.dio.post(
|
||||||
|
Urls.logout,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
static Future<Response> deleteAccount() {
|
||||||
|
return DioService.dio.post(
|
||||||
|
Urls.deleteAccount,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
static Future<Response> getAppConfig() {
|
||||||
|
Map<String, dynamic> query = {'ver': 0};
|
||||||
|
return DioService.dio.get(Urls.getAppConfig, queryParameters: query);
|
||||||
|
}
|
||||||
|
|
||||||
|
static Future<Response> saveUserInfo(Map<String, dynamic> data) {
|
||||||
|
return DioService.dio.post(Urls.saveUserInfo, data: data);
|
||||||
|
}
|
||||||
|
|
||||||
|
static Future<Response> uploadImg(File file,
|
||||||
|
{String? bussinessModule, String? bussinessRecordId}) async {
|
||||||
|
String fileName = file.path.split('/').last;
|
||||||
|
final filePath =
|
||||||
|
await MultipartFile.fromFile(file.path, filename: fileName);
|
||||||
|
final formData = FormData.fromMap({
|
||||||
|
'bussinessRecordId': bussinessRecordId,
|
||||||
|
'bussinessModule': bussinessModule,
|
||||||
|
'file': filePath,
|
||||||
|
});
|
||||||
|
return DioService.dio.post(Urls.uploadAttachemnt, data: formData);
|
||||||
|
}
|
||||||
|
|
||||||
|
static Future<Response> updateAvatar(String filename) {
|
||||||
|
return DioService.dio
|
||||||
|
.post(Urls.updateAvatar, data: {'avatarPath': filename});
|
||||||
|
}
|
||||||
|
}
|
|
@ -6,8 +6,8 @@ class Urls {
|
||||||
static String deleteAccount = 'user/deleteAccount';
|
static String deleteAccount = 'user/deleteAccount';
|
||||||
static String saveUserInfo = 'user/saveUserInfo';
|
static String saveUserInfo = 'user/saveUserInfo';
|
||||||
static String getUserInfo = 'account/profile';
|
static String getUserInfo = 'account/profile';
|
||||||
static String getProjects = 'project';
|
static String projects = 'project';
|
||||||
static String getProducts = 'product';
|
static String products = 'product';
|
||||||
static String inventoryInout = 'materials-in-out';
|
static String inventoryInout = 'materials-in-out';
|
||||||
static String inventory = 'materials-inventory';
|
static String inventory = 'materials-inventory';
|
||||||
static String updateAvatar = 'user/updateAvatar';
|
static String updateAvatar = 'user/updateAvatar';
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
import 'package:sk_base_mobile/constants/enum.dart';
|
import 'package:sk_base_mobile/constants/enum.dart';
|
||||||
import 'package:sk_base_mobile/models/file.model.dart';
|
import 'package:sk_base_mobile/models/file.model.dart';
|
||||||
import 'package:sk_base_mobile/models/index.dart';
|
import 'package:sk_base_mobile/models/index.dart';
|
||||||
|
import 'package:sk_base_mobile/models/inventory.model.dart';
|
||||||
import 'package:sk_base_mobile/models/product.model.dart';
|
import 'package:sk_base_mobile/models/product.model.dart';
|
||||||
import 'package:sk_base_mobile/models/project.model.dart';
|
import 'package:sk_base_mobile/models/project.model.dart';
|
||||||
|
|
||||||
|
@ -24,6 +25,7 @@ class InventoryInOutModel {
|
||||||
required this.files,
|
required this.files,
|
||||||
required this.project,
|
required this.project,
|
||||||
required this.product,
|
required this.product,
|
||||||
|
this.inventory,
|
||||||
});
|
});
|
||||||
|
|
||||||
final int? id;
|
final int? id;
|
||||||
|
@ -41,10 +43,10 @@ class InventoryInOutModel {
|
||||||
final String? remark;
|
final String? remark;
|
||||||
final int? projectId;
|
final int? projectId;
|
||||||
final int? isDelete;
|
final int? isDelete;
|
||||||
final List<FileModel?> files;
|
final List<FileModel> files;
|
||||||
final ProjectModel? project;
|
final ProjectModel? project;
|
||||||
final ProductModel? product;
|
final ProductModel? product;
|
||||||
|
final InventoryModel? inventory;
|
||||||
factory InventoryInOutModel.fromJson(Map<String, dynamic> json) {
|
factory InventoryInOutModel.fromJson(Map<String, dynamic> json) {
|
||||||
return InventoryInOutModel(
|
return InventoryInOutModel(
|
||||||
id: json["id"],
|
id: json["id"],
|
||||||
|
@ -72,6 +74,9 @@ class InventoryInOutModel {
|
||||||
product: json["product"] == null
|
product: json["product"] == null
|
||||||
? null
|
? null
|
||||||
: ProductModel.fromJson(json["product"]),
|
: ProductModel.fromJson(json["product"]),
|
||||||
|
inventory: json['inventory'] == null
|
||||||
|
? null
|
||||||
|
: InventoryModel.fromJson(json["inventory"]),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -94,5 +99,6 @@ class InventoryInOutModel {
|
||||||
"files": files.map((x) => x).toList(),
|
"files": files.map((x) => x).toList(),
|
||||||
"project": project?.toJson(),
|
"project": project?.toJson(),
|
||||||
"product": product?.toJson(),
|
"product": product?.toJson(),
|
||||||
|
"inventory": inventory?.toJson(),
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,14 @@
|
||||||
|
import 'package:flutter/material.dart';
|
||||||
|
import 'package:sk_base_mobile/screens/new_inventory_inout/components/inventory_search.dart';
|
||||||
|
|
||||||
|
class InventoryPage extends StatelessWidget {
|
||||||
|
const InventoryPage({super.key});
|
||||||
|
|
||||||
|
@override
|
||||||
|
Widget build(BuildContext context) {
|
||||||
|
return Scaffold(
|
||||||
|
appBar: AppBar(title: const Text('库存管理')),
|
||||||
|
body: InventorySearch(),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
|
@ -16,138 +16,144 @@ class InventoryInoutCard extends StatelessWidget {
|
||||||
final controller = Get.find<InventoryInoutController>();
|
final controller = Get.find<InventoryInoutController>();
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
return Container(
|
return InkWell(
|
||||||
margin: EdgeInsets.symmetric(
|
onTap: () {
|
||||||
vertical: ScreenAdaper.height(15),
|
controller
|
||||||
horizontal: ScreenAdaper.width(15)),
|
.showInventoryInoutInfoDialog(controller.list[ind][index].id!);
|
||||||
padding: EdgeInsets.symmetric(
|
},
|
||||||
horizontal: ScreenAdaper.width(defaultPadding),
|
child: Container(
|
||||||
vertical: ScreenAdaper.height(defaultPadding)),
|
margin: EdgeInsets.symmetric(
|
||||||
decoration: BoxDecoration(
|
vertical: ScreenAdaper.height(15),
|
||||||
boxShadow: [
|
horizontal: ScreenAdaper.width(15)),
|
||||||
BoxShadow(
|
padding: EdgeInsets.symmetric(
|
||||||
color: AppTheme.barrierColor.withOpacity(0.2),
|
horizontal: ScreenAdaper.width(defaultPadding),
|
||||||
offset: Offset(0, ScreenAdaper.height(5)),
|
vertical: ScreenAdaper.height(defaultPadding)),
|
||||||
blurRadius: ScreenAdaper.sp(10)),
|
decoration: BoxDecoration(
|
||||||
],
|
boxShadow: [
|
||||||
color: AppTheme.nearlyWhite,
|
BoxShadow(
|
||||||
borderRadius: BorderRadius.circular(ScreenAdaper.sp(30))),
|
color: AppTheme.barrierColor.withOpacity(0.2),
|
||||||
child: Row(
|
offset: Offset(0, ScreenAdaper.height(5)),
|
||||||
crossAxisAlignment: CrossAxisAlignment.center,
|
blurRadius: ScreenAdaper.sp(10)),
|
||||||
children: [
|
],
|
||||||
buildImage(),
|
color: AppTheme.nearlyWhite,
|
||||||
Expanded(child: buildContent()),
|
borderRadius: BorderRadius.circular(ScreenAdaper.sp(30))),
|
||||||
|
child: Row(
|
||||||
|
crossAxisAlignment: CrossAxisAlignment.center,
|
||||||
|
children: [
|
||||||
|
buildImage(),
|
||||||
|
Expanded(child: buildContent()),
|
||||||
|
|
||||||
// const Spacer(
|
// const Spacer(
|
||||||
// flex: 2,
|
// flex: 2,
|
||||||
// ),
|
// ),
|
||||||
// controller.list[ind][index].inOrOut ==
|
// controller.list[ind][index].inOrOut ==
|
||||||
// InventoryInOrOutEnumValues[InventoryInOrOutEnum.In]
|
// InventoryInOrOutEnumValues[InventoryInOrOutEnum.In]
|
||||||
// ? Container(
|
// ? Container(
|
||||||
// height: ScreenAdaper.height(40),
|
// height: ScreenAdaper.height(40),
|
||||||
// width: ScreenAdaper.width(40),
|
// width: ScreenAdaper.width(40),
|
||||||
// decoration: BoxDecoration(
|
// decoration: BoxDecoration(
|
||||||
// shape: BoxShape.circle,
|
// shape: BoxShape.circle,
|
||||||
// gradient: const LinearGradient(
|
// gradient: const LinearGradient(
|
||||||
// begin: Alignment.topCenter,
|
// begin: Alignment.topCenter,
|
||||||
// end: Alignment.bottomCenter,
|
// end: Alignment.bottomCenter,
|
||||||
// colors: [
|
// colors: [
|
||||||
// lightOrange,
|
// lightOrange,
|
||||||
// darkOrange,
|
// darkOrange,
|
||||||
// ]),
|
// ]),
|
||||||
// boxShadow: [
|
// boxShadow: [
|
||||||
// BoxShadow(
|
// BoxShadow(
|
||||||
// color: lightOrange,
|
// color: lightOrange,
|
||||||
// offset: Offset(0, ScreenAdaper.height(10)),
|
// offset: Offset(0, ScreenAdaper.height(10)),
|
||||||
// blurRadius: ScreenAdaper.sp(10))
|
// blurRadius: ScreenAdaper.sp(10))
|
||||||
// ]),
|
// ]),
|
||||||
// child: const Icon(
|
// child: const Icon(
|
||||||
// Icons.done,
|
// Icons.done,
|
||||||
// color: Colors.white,
|
// color: Colors.white,
|
||||||
// ),
|
// ),
|
||||||
// )
|
// )
|
||||||
// : Align(
|
// : Align(
|
||||||
// alignment: Alignment.topRight,
|
// alignment: Alignment.topRight,
|
||||||
// child: Padding(
|
// child: Padding(
|
||||||
// padding: EdgeInsets.only(top: ScreenAdaper.height(20)),
|
// padding: EdgeInsets.only(top: ScreenAdaper.height(20)),
|
||||||
// child: PopupMenuButton(
|
// child: PopupMenuButton(
|
||||||
// onSelected: (value) => {
|
// onSelected: (value) => {
|
||||||
// // controller.onTaskComplete(value, index, ind,
|
// // controller.onTaskComplete(value, index, ind,
|
||||||
// // controller.list[ind][index].key, context)
|
// // controller.list[ind][index].key, context)
|
||||||
// },
|
// },
|
||||||
// surfaceTintColor: Colors.white,
|
// surfaceTintColor: Colors.white,
|
||||||
// padding: EdgeInsets.zero,
|
// padding: EdgeInsets.zero,
|
||||||
// icon: Icon(
|
// icon: Icon(
|
||||||
// Icons.more_vert_rounded,
|
// Icons.more_vert_rounded,
|
||||||
// color: Colors.grey,
|
// color: Colors.grey,
|
||||||
// size: ScreenAdaper.sp(24),
|
// size: ScreenAdaper.sp(24),
|
||||||
// ),
|
// ),
|
||||||
// shape: OutlineInputBorder(
|
// shape: OutlineInputBorder(
|
||||||
// borderRadius:
|
// borderRadius:
|
||||||
// BorderRadius.circular(ScreenAdaper.sp(20)),
|
// BorderRadius.circular(ScreenAdaper.sp(20)),
|
||||||
// borderSide: BorderSide.none,
|
// borderSide: BorderSide.none,
|
||||||
// ),
|
// ),
|
||||||
// itemBuilder: (context) {
|
// itemBuilder: (context) {
|
||||||
// return [
|
// return [
|
||||||
// PopupMenuItem(
|
// PopupMenuItem(
|
||||||
// height: ScreenAdaper.height(20),
|
// height: ScreenAdaper.height(20),
|
||||||
// value: 1,
|
// value: 1,
|
||||||
// child: Row(
|
// child: Row(
|
||||||
// children: [
|
// children: [
|
||||||
// Icon(
|
// Icon(
|
||||||
// Icons.edit_note,
|
// Icons.edit_note,
|
||||||
// color: Colors.orange,
|
// color: Colors.orange,
|
||||||
// size: ScreenAdaper.sp(14),
|
// size: ScreenAdaper.sp(14),
|
||||||
// ),
|
// ),
|
||||||
// SizedBox(
|
// SizedBox(
|
||||||
// width:
|
// width:
|
||||||
// ScreenAdaper.width(defaultPadding) /
|
// ScreenAdaper.width(defaultPadding) /
|
||||||
// 2,
|
// 2,
|
||||||
// ),
|
// ),
|
||||||
// const Text('Edit')
|
// const Text('Edit')
|
||||||
// ],
|
// ],
|
||||||
// )),
|
// )),
|
||||||
// PopupMenuItem(
|
// PopupMenuItem(
|
||||||
// height: ScreenAdaper.height(25),
|
// height: ScreenAdaper.height(25),
|
||||||
// value: 2,
|
// value: 2,
|
||||||
// child: Row(
|
// child: Row(
|
||||||
// children: [
|
// children: [
|
||||||
// Icon(
|
// Icon(
|
||||||
// Icons.delete_outline,
|
// Icons.delete_outline,
|
||||||
// color: Colors.orange,
|
// color: Colors.orange,
|
||||||
// size: ScreenAdaper.sp(14),
|
// size: ScreenAdaper.sp(14),
|
||||||
// ),
|
// ),
|
||||||
// SizedBox(
|
// SizedBox(
|
||||||
// width:
|
// width:
|
||||||
// ScreenAdaper.width(defaultPadding) /
|
// ScreenAdaper.width(defaultPadding) /
|
||||||
// 2,
|
// 2,
|
||||||
// ),
|
// ),
|
||||||
// Text('Delete')
|
// Text('Delete')
|
||||||
// ],
|
// ],
|
||||||
// )),
|
// )),
|
||||||
// PopupMenuItem(
|
// PopupMenuItem(
|
||||||
// height: ScreenAdaper.height(25),
|
// height: ScreenAdaper.height(25),
|
||||||
// value: 3,
|
// value: 3,
|
||||||
// child: Row(
|
// child: Row(
|
||||||
// children: [
|
// children: [
|
||||||
// Icon(
|
// Icon(
|
||||||
// Icons.done_all_outlined,
|
// Icons.done_all_outlined,
|
||||||
// color: Colors.orange,
|
// color: Colors.orange,
|
||||||
// size: ScreenAdaper.sp(14),
|
// size: ScreenAdaper.sp(14),
|
||||||
// ),
|
// ),
|
||||||
// SizedBox(
|
// SizedBox(
|
||||||
// width:
|
// width:
|
||||||
// ScreenAdaper.width(defaultPadding) /
|
// ScreenAdaper.width(defaultPadding) /
|
||||||
// 2,
|
// 2,
|
||||||
// ),
|
// ),
|
||||||
// Text('Complete')
|
// Text('Complete')
|
||||||
// ],
|
// ],
|
||||||
// )),
|
// )),
|
||||||
// ];
|
// ];
|
||||||
// },
|
// },
|
||||||
// )),
|
// )),
|
||||||
// ),
|
// ),
|
||||||
],
|
],
|
||||||
|
),
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -224,9 +230,8 @@ class InventoryInoutCard extends StatelessWidget {
|
||||||
child: FadeInCacheImage(
|
child: FadeInCacheImage(
|
||||||
width: ScreenAdaper.width(100),
|
width: ScreenAdaper.width(100),
|
||||||
height: ScreenAdaper.width(100),
|
height: ScreenAdaper.width(100),
|
||||||
url: controller.list[ind][index].product?.files.isNotEmpty ??
|
url: controller.list[ind][index].files.isNotEmpty
|
||||||
false
|
? '${GloablConfig.OSS_URL}${controller.list[ind][index].files[0]?.path}'
|
||||||
? '${GloablConfig.OSS_URL}${controller.list[ind][index].product?.files[0].path}'
|
|
||||||
: ''),
|
: ''),
|
||||||
));
|
));
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,190 @@
|
||||||
|
import 'package:flutter/material.dart';
|
||||||
|
import 'package:get/get.dart';
|
||||||
|
import 'package:loading_animation_widget/loading_animation_widget.dart';
|
||||||
|
import 'package:sk_base_mobile/apis/index.dart';
|
||||||
|
import 'package:sk_base_mobile/app_theme.dart';
|
||||||
|
import 'package:sk_base_mobile/config.dart';
|
||||||
|
import 'package:sk_base_mobile/constants/bg_color.dart';
|
||||||
|
import 'package:sk_base_mobile/constants/constants.dart';
|
||||||
|
import 'package:sk_base_mobile/models/index.dart';
|
||||||
|
import 'package:sk_base_mobile/models/inventory.model.dart';
|
||||||
|
import 'package:sk_base_mobile/util/date.util.dart';
|
||||||
|
import 'package:sk_base_mobile/util/screen_adaper_util.dart';
|
||||||
|
import 'package:sk_base_mobile/widgets/empty.dart';
|
||||||
|
import 'package:sk_base_mobile/widgets/fade_in_cache_image.dart';
|
||||||
|
import 'package:sk_base_mobile/widgets/image_preview.dart';
|
||||||
|
import 'package:sk_base_mobile/widgets/loading_indicator.dart';
|
||||||
|
|
||||||
|
class InventoryInoutInfo extends StatelessWidget {
|
||||||
|
late int inventoryInoutId;
|
||||||
|
late InventoryInouInfoController controller;
|
||||||
|
InventoryInoutInfo({Key? key, required this.inventoryInoutId})
|
||||||
|
: controller = Get.put(InventoryInouInfoController(inventoryInoutId)),
|
||||||
|
super(key: key);
|
||||||
|
|
||||||
|
@override
|
||||||
|
Widget build(BuildContext context) {
|
||||||
|
return SizedBox(
|
||||||
|
child: Column(children: [
|
||||||
|
Container(
|
||||||
|
padding: EdgeInsets.symmetric(
|
||||||
|
horizontal: ScreenAdaper.width(10),
|
||||||
|
vertical: ScreenAdaper.height(15)),
|
||||||
|
decoration: const BoxDecoration(color: AppTheme.primaryColor),
|
||||||
|
child: Row(
|
||||||
|
mainAxisAlignment: MainAxisAlignment.center,
|
||||||
|
children: [
|
||||||
|
Text(
|
||||||
|
'出入库详情',
|
||||||
|
style: TextStyle(
|
||||||
|
fontSize: ScreenAdaper.sp(25), color: AppTheme.nearlyWhite),
|
||||||
|
),
|
||||||
|
],
|
||||||
|
),
|
||||||
|
),
|
||||||
|
Expanded(
|
||||||
|
child: Obx(() => controller.inventoryInoutInfo.value == null
|
||||||
|
? const Center(child: LoadingIndicator(common: true))
|
||||||
|
: SingleChildScrollView(
|
||||||
|
child: Column(
|
||||||
|
children: [
|
||||||
|
buildListItem(
|
||||||
|
leading: '出入库类型',
|
||||||
|
trailing: InventoryInOrOutEnum.In ==
|
||||||
|
controller.inventoryInoutInfo.value?.inOrOut
|
||||||
|
? '入库'
|
||||||
|
: '出库'),
|
||||||
|
customDivider(),
|
||||||
|
if (InventoryInOrOutEnum.In ==
|
||||||
|
controller.inventoryInoutInfo.value?.inOrOut) ...[
|
||||||
|
buildListItem(
|
||||||
|
leading: '存放位置',
|
||||||
|
trailing: controller
|
||||||
|
.inventoryInoutInfo.value?.inventory?.position),
|
||||||
|
customDivider(),
|
||||||
|
],
|
||||||
|
buildListItem(
|
||||||
|
leading: '出入库时间',
|
||||||
|
trailing: DateUtil.format(
|
||||||
|
controller.inventoryInoutInfo.value!.time!)),
|
||||||
|
customDivider(),
|
||||||
|
buildListItem(
|
||||||
|
leading: '所属公司',
|
||||||
|
trailing: controller.inventoryInoutInfo.value?.product
|
||||||
|
?.company?.name),
|
||||||
|
customDivider(),
|
||||||
|
buildListItem(
|
||||||
|
leading: '产品名称',
|
||||||
|
trailing: controller
|
||||||
|
.inventoryInoutInfo.value?.product?.name),
|
||||||
|
customDivider(),
|
||||||
|
buildListItem(
|
||||||
|
leading: '产品规格',
|
||||||
|
trailing: controller.inventoryInoutInfo.value?.product
|
||||||
|
?.productSpecification),
|
||||||
|
customDivider(),
|
||||||
|
buildListItem(
|
||||||
|
leading: '数量',
|
||||||
|
trailing:
|
||||||
|
'${controller.inventoryInoutInfo.value?.quantity}${controller.inventoryInoutInfo.value?.product?.unit?.label ?? ''}'),
|
||||||
|
customDivider(),
|
||||||
|
buildListItem(
|
||||||
|
leading: '单价',
|
||||||
|
trailing:
|
||||||
|
'¥${double.parse('${controller.inventoryInoutInfo.value?.unitPrice ?? 0}')}'),
|
||||||
|
customDivider(),
|
||||||
|
buildListItem(
|
||||||
|
leading: '操作人',
|
||||||
|
trailing: controller.inventoryInoutInfo.value?.agent),
|
||||||
|
customDivider(),
|
||||||
|
buildListItem(
|
||||||
|
leading: '备注',
|
||||||
|
trailing:
|
||||||
|
controller.inventoryInoutInfo.value?.remark),
|
||||||
|
customDivider(),
|
||||||
|
buildListItem(
|
||||||
|
leading: '照片',
|
||||||
|
),
|
||||||
|
buildAttachmentsPreview()
|
||||||
|
],
|
||||||
|
))))
|
||||||
|
]),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
Widget buildAttachmentsPreview() {
|
||||||
|
return Container(
|
||||||
|
padding: EdgeInsets.symmetric(vertical: ScreenAdaper.height(20)),
|
||||||
|
child: Wrap(
|
||||||
|
spacing: ScreenAdaper.width(10),
|
||||||
|
runSpacing: ScreenAdaper.height(10),
|
||||||
|
children: (controller.inventoryInoutInfo.value?.files ?? [])
|
||||||
|
.map((e) => buildImage(e.path))
|
||||||
|
.toList(),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
Widget buildImage(String? path) {
|
||||||
|
return path == null
|
||||||
|
? const SizedBox()
|
||||||
|
: InkWell(
|
||||||
|
onTap: () => {
|
||||||
|
if (controller.inventoryInoutInfo.value!.files.isNotEmpty)
|
||||||
|
{
|
||||||
|
Get.dialog(ImagePreivew(
|
||||||
|
galleryItems: controller.inventoryInoutInfo.value!.files,
|
||||||
|
initialIndex: controller.inventoryInoutInfo.value!.files
|
||||||
|
.indexWhere((element) => element.path == path)))
|
||||||
|
}
|
||||||
|
},
|
||||||
|
child: Container(
|
||||||
|
margin: EdgeInsets.only(
|
||||||
|
right: ScreenAdaper.width(defaultPadding) / 2),
|
||||||
|
child: ClipRRect(
|
||||||
|
borderRadius: BorderRadius.circular(ScreenAdaper.sp(15)),
|
||||||
|
child: FadeInCacheImage(
|
||||||
|
width: ScreenAdaper.width(300),
|
||||||
|
height: ScreenAdaper.width(300),
|
||||||
|
url: '${GloablConfig.OSS_URL}$path'),
|
||||||
|
)),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
Widget customDivider() {
|
||||||
|
return Divider(
|
||||||
|
height: ScreenAdaper.height(1),
|
||||||
|
color: AppTheme.dividerColor,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
Widget buildListItem({String? leading, dynamic trailing}) {
|
||||||
|
return ListTile(
|
||||||
|
leading: Text(
|
||||||
|
'${leading ?? ''}: ',
|
||||||
|
style: TextStyle(fontSize: ScreenAdaper.sp(25)),
|
||||||
|
),
|
||||||
|
trailing: Text('${trailing ?? ''}',
|
||||||
|
style: TextStyle(fontSize: ScreenAdaper.sp(25))));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
class InventoryInouInfoController extends GetxController {
|
||||||
|
final inventoryInoutInfo = Rx<InventoryInOutModel?>(null);
|
||||||
|
int inventoryInoutId;
|
||||||
|
InventoryInouInfoController(this.inventoryInoutId);
|
||||||
|
|
||||||
|
@override
|
||||||
|
onReady() {
|
||||||
|
getData();
|
||||||
|
}
|
||||||
|
|
||||||
|
Future<void> getData() async {
|
||||||
|
printInfo(info: '$inventoryInoutId');
|
||||||
|
await Future.delayed(const Duration(milliseconds: 500));
|
||||||
|
final res = await Api.getInventoryInOutInfo(inventoryInoutId);
|
||||||
|
if (res.data != null) {
|
||||||
|
inventoryInoutInfo.value = InventoryInOutModel.fromJson(res.data);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -1,14 +1,15 @@
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:get/get.dart';
|
import 'package:get/get.dart';
|
||||||
|
import 'package:sk_base_mobile/apis/index.dart';
|
||||||
import 'package:sk_base_mobile/app_theme.dart';
|
import 'package:sk_base_mobile/app_theme.dart';
|
||||||
import 'package:sk_base_mobile/constants/enum.dart';
|
import 'package:sk_base_mobile/constants/enum.dart';
|
||||||
import 'package:sk_base_mobile/db_helper/dbHelper.dart';
|
import 'package:sk_base_mobile/db_helper/dbHelper.dart';
|
||||||
|
import 'package:sk_base_mobile/screens/inventory_inout/components/inventory_inout_info.dart';
|
||||||
import 'package:sk_base_mobile/screens/new_inventory_inout/new_inventory_inout.dart';
|
import 'package:sk_base_mobile/screens/new_inventory_inout/new_inventory_inout.dart';
|
||||||
import 'package:sk_base_mobile/util/date.util.dart';
|
import 'package:sk_base_mobile/util/date.util.dart';
|
||||||
import 'package:sk_base_mobile/util/logger_util.dart';
|
import 'package:sk_base_mobile/util/logger_util.dart';
|
||||||
import 'package:sk_base_mobile/util/modal.util.dart';
|
import 'package:sk_base_mobile/util/modal.util.dart';
|
||||||
import 'package:sk_base_mobile/util/screen_adaper_util.dart';
|
import 'package:sk_base_mobile/util/screen_adaper_util.dart';
|
||||||
import 'package:sk_base_mobile/apis/api.dart' as Api;
|
|
||||||
import '../../models/index.dart';
|
import '../../models/index.dart';
|
||||||
import 'components/responsive.dart';
|
import 'components/responsive.dart';
|
||||||
|
|
||||||
|
@ -243,6 +244,14 @@ class InventoryInoutController extends GetxController {
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Future showInventoryInoutInfoDialog(int id) async {
|
||||||
|
ModalUtil.showGeneralDialog(
|
||||||
|
width: ScreenAdaper.width(Get.width - 100),
|
||||||
|
height: ScreenAdaper.height(Get.height - 100),
|
||||||
|
content: InventoryInoutInfo(inventoryInoutId: id))
|
||||||
|
.then((value) => {Get.delete<InventoryInouInfoController>()});
|
||||||
|
}
|
||||||
|
|
||||||
Future<List<InventoryInOutModel>> getInoutHistory() async {
|
Future<List<InventoryInOutModel>> getInoutHistory() async {
|
||||||
final res = await Api.getInventoryInout({});
|
final res = await Api.getInventoryInout({});
|
||||||
printInfo(info: res.toString());
|
printInfo(info: res.toString());
|
||||||
|
|
|
@ -21,7 +21,9 @@ class LandingPage extends StatelessWidget {
|
||||||
child: Obx(() => Scaffold(
|
child: Obx(() => Scaffold(
|
||||||
floatingActionButtonLocation:
|
floatingActionButtonLocation:
|
||||||
FloatingActionButtonLocation.centerDocked,
|
FloatingActionButtonLocation.centerDocked,
|
||||||
floatingActionButton: controller.currentIndex.value == 0
|
floatingActionButton: [0].indexWhere(
|
||||||
|
(item) => item == controller.currentIndex.value) >
|
||||||
|
-1
|
||||||
? FloatingCreateButton()
|
? FloatingCreateButton()
|
||||||
: null,
|
: null,
|
||||||
bottomNavigationBar: BottomNavBar(),
|
bottomNavigationBar: BottomNavBar(),
|
||||||
|
|
|
@ -2,7 +2,7 @@ import 'package:flutter/cupertino.dart';
|
||||||
import 'package:get/get.dart';
|
import 'package:get/get.dart';
|
||||||
import 'package:sk_base_mobile/models/user_info.model.dart';
|
import 'package:sk_base_mobile/models/user_info.model.dart';
|
||||||
import 'package:sk_base_mobile/store/auth.store.dart';
|
import 'package:sk_base_mobile/store/auth.store.dart';
|
||||||
import 'package:sk_base_mobile/apis/api.dart' as Api;
|
import 'package:sk_base_mobile/apis/index.dart';
|
||||||
|
|
||||||
class UserInfoController extends GetxController {
|
class UserInfoController extends GetxController {
|
||||||
final nickNameController = TextEditingController(text: '');
|
final nickNameController = TextEditingController(text: '');
|
||||||
|
|
|
@ -3,13 +3,13 @@ import 'dart:async';
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:get/get.dart';
|
import 'package:get/get.dart';
|
||||||
import 'package:pull_to_refresh/pull_to_refresh.dart';
|
import 'package:pull_to_refresh/pull_to_refresh.dart';
|
||||||
|
import 'package:sk_base_mobile/apis/index.dart';
|
||||||
import 'package:sk_base_mobile/app_theme.dart';
|
import 'package:sk_base_mobile/app_theme.dart';
|
||||||
import 'package:sk_base_mobile/constants/bg_color.dart';
|
import 'package:sk_base_mobile/constants/bg_color.dart';
|
||||||
import 'package:sk_base_mobile/models/index.dart';
|
import 'package:sk_base_mobile/models/index.dart';
|
||||||
import 'package:sk_base_mobile/models/inventory.model.dart';
|
import 'package:sk_base_mobile/models/inventory.model.dart';
|
||||||
import 'package:sk_base_mobile/util/debouncer.dart';
|
import 'package:sk_base_mobile/util/debouncer.dart';
|
||||||
import 'package:sk_base_mobile/util/screen_adaper_util.dart';
|
import 'package:sk_base_mobile/util/screen_adaper_util.dart';
|
||||||
import 'package:sk_base_mobile/apis/api.dart' as Api;
|
|
||||||
|
|
||||||
class InventorySearch extends StatelessWidget {
|
class InventorySearch extends StatelessWidget {
|
||||||
Function(InventoryModel)? onInventorySelected;
|
Function(InventoryModel)? onInventorySelected;
|
||||||
|
|
|
@ -3,12 +3,12 @@ import 'dart:async';
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:get/get.dart';
|
import 'package:get/get.dart';
|
||||||
import 'package:pull_to_refresh/pull_to_refresh.dart';
|
import 'package:pull_to_refresh/pull_to_refresh.dart';
|
||||||
|
import 'package:sk_base_mobile/apis/index.dart';
|
||||||
import 'package:sk_base_mobile/app_theme.dart';
|
import 'package:sk_base_mobile/app_theme.dart';
|
||||||
import 'package:sk_base_mobile/constants/bg_color.dart';
|
import 'package:sk_base_mobile/constants/bg_color.dart';
|
||||||
import 'package:sk_base_mobile/models/index.dart';
|
import 'package:sk_base_mobile/models/index.dart';
|
||||||
import 'package:sk_base_mobile/util/debouncer.dart';
|
import 'package:sk_base_mobile/util/debouncer.dart';
|
||||||
import 'package:sk_base_mobile/util/screen_adaper_util.dart';
|
import 'package:sk_base_mobile/util/screen_adaper_util.dart';
|
||||||
import 'package:sk_base_mobile/apis/api.dart' as Api;
|
|
||||||
|
|
||||||
class ProductSearch extends StatelessWidget {
|
class ProductSearch extends StatelessWidget {
|
||||||
Function(ProductModel)? onProductSelected;
|
Function(ProductModel)? onProductSelected;
|
||||||
|
|
|
@ -202,34 +202,35 @@ class NewInventoryInout extends StatelessWidget {
|
||||||
));
|
));
|
||||||
} else {
|
} else {
|
||||||
ModalUtil.showGeneralDialog(
|
ModalUtil.showGeneralDialog(
|
||||||
content: InventorySearch(
|
content: InventorySearch(
|
||||||
beforeSelectedCheck: (InventoryModel itemData) {
|
beforeSelectedCheck: (InventoryModel itemData) {
|
||||||
final isValid = (itemData.quantity ?? 0) > 0;
|
final isValid = (itemData.quantity ?? 0) > 0;
|
||||||
if (!isValid) {
|
if (!isValid) {
|
||||||
SnackBarUtil().warning('库存不足');
|
SnackBarUtil().warning('库存不足');
|
||||||
}
|
}
|
||||||
return (itemData.quantity ?? 0) > 0;
|
return (itemData.quantity ?? 0) > 0;
|
||||||
},
|
},
|
||||||
onInventorySelected: (InventoryModel inventory) {
|
onInventorySelected: (InventoryModel inventory) {
|
||||||
Get.back();
|
Get.back();
|
||||||
controller.payload['inventoryId'] = inventory.id;
|
controller.payload['inventoryId'] = inventory.id;
|
||||||
String productName =
|
String productName =
|
||||||
'${inventory.product!.name!}(¥${double.parse('${inventory.unitPrice}')})(${inventory.product?.company?.name})';
|
'${inventory.product!.name!}(¥${double.parse('${inventory.unitPrice}')})(${inventory.product?.company?.name})';
|
||||||
if ((inventory.product?.productSpecification ?? '')
|
if ((inventory.product?.productSpecification ?? '')
|
||||||
.isNotEmpty) {
|
.isNotEmpty) {
|
||||||
productName +=
|
productName +=
|
||||||
' (${inventory.product?.productSpecification})';
|
' (${inventory.product?.productSpecification})';
|
||||||
}
|
}
|
||||||
controller.projectTextController.text =
|
controller.projectTextController.text =
|
||||||
inventory.project!.name!;
|
inventory.project!.name!;
|
||||||
controller.payload['projectId'] = inventory.project?.id;
|
controller.payload['projectId'] = inventory.project?.id;
|
||||||
controller.quantityTextController.text =
|
controller.quantityTextController.text =
|
||||||
'${inventory.quantity}';
|
'${inventory.quantity}';
|
||||||
controller.productTextController.text = productName;
|
controller.productTextController.text = productName;
|
||||||
controller.payload['productId'] = inventory.product?.id;
|
controller.payload['productId'] = inventory.product?.id;
|
||||||
},
|
},
|
||||||
),
|
),
|
||||||
width: Get.width - ScreenAdaper.width(50));
|
width: Get.width - ScreenAdaper.width(50))
|
||||||
|
.then((value) => Get.delete<InventorySearchController>());
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
|
@ -4,11 +4,11 @@ import 'package:decimal/decimal.dart';
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:get/get.dart';
|
import 'package:get/get.dart';
|
||||||
import 'package:image_picker/image_picker.dart';
|
import 'package:image_picker/image_picker.dart';
|
||||||
|
import 'package:sk_base_mobile/apis/index.dart';
|
||||||
import 'package:sk_base_mobile/constants/enum.dart';
|
import 'package:sk_base_mobile/constants/enum.dart';
|
||||||
import 'package:sk_base_mobile/db_helper/dbHelper.dart';
|
import 'package:sk_base_mobile/db_helper/dbHelper.dart';
|
||||||
import 'package:sk_base_mobile/models/index.dart';
|
import 'package:sk_base_mobile/models/index.dart';
|
||||||
import 'package:sk_base_mobile/screens/inventory_inout/inventory_inout_controller.dart';
|
import 'package:sk_base_mobile/screens/inventory_inout/inventory_inout_controller.dart';
|
||||||
import 'package:sk_base_mobile/apis/api.dart' as Api;
|
|
||||||
import 'package:sk_base_mobile/util/date.util.dart';
|
import 'package:sk_base_mobile/util/date.util.dart';
|
||||||
import 'package:sk_base_mobile/util/logger_util.dart';
|
import 'package:sk_base_mobile/util/logger_util.dart';
|
||||||
import 'package:sk_base_mobile/util/media_util.dart';
|
import 'package:sk_base_mobile/util/media_util.dart';
|
||||||
|
|
|
@ -7,8 +7,9 @@ import 'package:package_info/package_info.dart';
|
||||||
import 'package:sk_base_mobile/app_theme.dart';
|
import 'package:sk_base_mobile/app_theme.dart';
|
||||||
import 'package:sk_base_mobile/models/app_bottom_nav_item.dart';
|
import 'package:sk_base_mobile/models/app_bottom_nav_item.dart';
|
||||||
import 'package:sk_base_mobile/models/app_config.dart';
|
import 'package:sk_base_mobile/models/app_config.dart';
|
||||||
|
import 'package:sk_base_mobile/screens/inventory/inventory.dart';
|
||||||
import 'package:sk_base_mobile/screens/inventory_inout/inventory_inout.dart';
|
import 'package:sk_base_mobile/screens/inventory_inout/inventory_inout.dart';
|
||||||
import 'package:sk_base_mobile/apis/api.dart' as Api;
|
import 'package:sk_base_mobile/apis/index.dart';
|
||||||
import 'package:sk_base_mobile/screens/workbench/workbench.dart';
|
import 'package:sk_base_mobile/screens/workbench/workbench.dart';
|
||||||
import 'package:sk_base_mobile/services/service.dart';
|
import 'package:sk_base_mobile/services/service.dart';
|
||||||
import 'package:sk_base_mobile/store/auth.store.dart';
|
import 'package:sk_base_mobile/store/auth.store.dart';
|
||||||
|
@ -36,7 +37,7 @@ class AppInfoService extends GetxService {
|
||||||
icon: Icons.inventory_outlined,
|
icon: Icons.inventory_outlined,
|
||||||
activeIcon: Icons.inventory_rounded,
|
activeIcon: Icons.inventory_rounded,
|
||||||
label: '库存',
|
label: '库存',
|
||||||
page: InvenotryInoutPage()),
|
page: InventoryPage()),
|
||||||
AppBottomNavItem(
|
AppBottomNavItem(
|
||||||
icon: Icons.widgets_outlined,
|
icon: Icons.widgets_outlined,
|
||||||
activeIcon: Icons.widgets_rounded,
|
activeIcon: Icons.widgets_rounded,
|
||||||
|
|
|
@ -16,7 +16,7 @@ class DioService extends Get.GetxService {
|
||||||
static late Dio _dio;
|
static late Dio _dio;
|
||||||
List<String> whiteList = [Urls.login];
|
List<String> whiteList = [Urls.login];
|
||||||
BaseOptions dioBaseOptions = BaseOptions(
|
BaseOptions dioBaseOptions = BaseOptions(
|
||||||
connectTimeout: const Duration(seconds: 5),
|
connectTimeout: const Duration(seconds: 20),
|
||||||
baseUrl: '${GloablConfig.BASE_URL}',
|
baseUrl: '${GloablConfig.BASE_URL}',
|
||||||
followRedirects: true);
|
followRedirects: true);
|
||||||
|
|
||||||
|
|
|
@ -2,7 +2,7 @@ import 'dart:convert';
|
||||||
|
|
||||||
import 'package:dio/dio.dart' as Dio;
|
import 'package:dio/dio.dart' as Dio;
|
||||||
import 'package:get/get.dart';
|
import 'package:get/get.dart';
|
||||||
import 'package:sk_base_mobile/apis/api.dart' as Api;
|
import 'package:sk_base_mobile/apis/index.dart';
|
||||||
import 'package:sk_base_mobile/util/logger_util.dart';
|
import 'package:sk_base_mobile/util/logger_util.dart';
|
||||||
import 'package:sk_base_mobile/widgets/tap_to_dismiss_keyboard.dart';
|
import 'package:sk_base_mobile/widgets/tap_to_dismiss_keyboard.dart';
|
||||||
import 'package:sk_base_mobile/models/auth.dart';
|
import 'package:sk_base_mobile/models/auth.dart';
|
||||||
|
@ -53,7 +53,6 @@ class AuthStore extends GetxController {
|
||||||
}
|
}
|
||||||
|
|
||||||
Future<void> logout({bool force = false}) async {
|
Future<void> logout({bool force = false}) async {
|
||||||
LoadingUtil.to.show(status: 'Logout...');
|
|
||||||
await StorageService.to.remove(CacheKeys.token, isWithUser: false);
|
await StorageService.to.remove(CacheKeys.token, isWithUser: false);
|
||||||
await StorageService.to.remove(CacheKeys.userInfo, isWithUser: false);
|
await StorageService.to.remove(CacheKeys.userInfo, isWithUser: false);
|
||||||
try {
|
try {
|
||||||
|
|
|
@ -3,7 +3,7 @@ import 'package:get/get_state_manager/get_state_manager.dart';
|
||||||
import 'package:sk_base_mobile/constants/dict_enum.dart';
|
import 'package:sk_base_mobile/constants/dict_enum.dart';
|
||||||
import 'package:sk_base_mobile/models/dict_item.model.dart';
|
import 'package:sk_base_mobile/models/dict_item.model.dart';
|
||||||
import 'package:sk_base_mobile/models/dict_type.model.dart';
|
import 'package:sk_base_mobile/models/dict_type.model.dart';
|
||||||
import 'package:sk_base_mobile/apis/api.dart' as Api;
|
import 'package:sk_base_mobile/apis/index.dart';
|
||||||
import 'package:sk_base_mobile/util/logger_util.dart';
|
import 'package:sk_base_mobile/util/logger_util.dart';
|
||||||
|
|
||||||
const needCachedKey = [
|
const needCachedKey = [
|
||||||
|
|
|
@ -4,9 +4,8 @@ import 'package:loading_animation_widget/loading_animation_widget.dart';
|
||||||
import 'package:sk_base_mobile/app_theme.dart';
|
import 'package:sk_base_mobile/app_theme.dart';
|
||||||
import 'package:sk_base_mobile/util/screen_adaper_util.dart';
|
import 'package:sk_base_mobile/util/screen_adaper_util.dart';
|
||||||
|
|
||||||
class LoadingUtil extends GetxController {
|
class LoadingUtil extends GetxService {
|
||||||
static LoadingUtil get to => Get.find();
|
static LoadingUtil get to => Get.find();
|
||||||
|
|
||||||
OverlayEntry? _loadingOverlay;
|
OverlayEntry? _loadingOverlay;
|
||||||
|
|
||||||
Future<LoadingUtil> init() async {
|
Future<LoadingUtil> init() async {
|
||||||
|
@ -53,8 +52,9 @@ class LoadingUtil extends GetxController {
|
||||||
));
|
));
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
if (Get.overlayContext != null) {
|
||||||
Overlay.of(Get.overlayContext!).insert(_loadingOverlay!);
|
Overlay.of(Get.overlayContext!).insert(_loadingOverlay!);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
hideLoading() {
|
hideLoading() {
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
import 'dart:io';
|
import 'dart:io';
|
||||||
import 'package:dio/dio.dart' as Dio;
|
import 'package:dio/dio.dart' as Dio;
|
||||||
import 'package:sk_base_mobile/apis/api.dart' as Api;
|
import 'package:sk_base_mobile/apis/index.dart';
|
||||||
import 'package:image_picker/image_picker.dart';
|
import 'package:image_picker/image_picker.dart';
|
||||||
import 'package:sk_base_mobile/models/upload_result.model.dart';
|
import 'package:sk_base_mobile/models/upload_result.model.dart';
|
||||||
import 'package:sk_base_mobile/services/service.dart';
|
import 'package:sk_base_mobile/services/service.dart';
|
||||||
|
@ -15,7 +15,7 @@ class MediaUtil {
|
||||||
}
|
}
|
||||||
AppInfoService.to.isCameraing.value = true;
|
AppInfoService.to.isCameraing.value = true;
|
||||||
pickedFile = await ImagePicker()
|
pickedFile = await ImagePicker()
|
||||||
.pickImage(source: ImageSource.camera, maxWidth: maxWidth ?? 400);
|
.pickImage(source: ImageSource.camera, maxWidth: maxWidth ?? 2000);
|
||||||
AppInfoService.to.isCameraing.value = false;
|
AppInfoService.to.isCameraing.value = false;
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
AppInfoService.to.isCameraing.value = false;
|
AppInfoService.to.isCameraing.value = false;
|
||||||
|
|
|
@ -68,7 +68,7 @@ class ModalUtil {
|
||||||
);
|
);
|
||||||
|
|
||||||
static Future<void> showGeneralDialog(
|
static Future<void> showGeneralDialog(
|
||||||
{required Widget content, double? width}) {
|
{required Widget content, double? width, double? height}) {
|
||||||
return Get.generalDialog(
|
return Get.generalDialog(
|
||||||
barrierLabel: "productPicker",
|
barrierLabel: "productPicker",
|
||||||
barrierDismissible: true,
|
barrierDismissible: true,
|
||||||
|
@ -79,7 +79,7 @@ class ModalUtil {
|
||||||
borderRadius: BorderRadius.circular(ScreenAdaper.sp(30)),
|
borderRadius: BorderRadius.circular(ScreenAdaper.sp(30)),
|
||||||
child: Material(
|
child: Material(
|
||||||
child: SizedBox(
|
child: SizedBox(
|
||||||
height: Get.height - ScreenAdaper.height(150),
|
height: height ?? Get.height - ScreenAdaper.height(150),
|
||||||
width: width ?? Get.width - ScreenAdaper.width(150),
|
width: width ?? Get.width - ScreenAdaper.width(150),
|
||||||
child: content,
|
child: content,
|
||||||
))));
|
))));
|
||||||
|
|
|
@ -0,0 +1,112 @@
|
||||||
|
import 'package:flutter/material.dart';
|
||||||
|
import 'package:get/get.dart';
|
||||||
|
import 'package:photo_view/photo_view.dart';
|
||||||
|
import 'package:photo_view/photo_view_gallery.dart';
|
||||||
|
import 'package:sk_base_mobile/config.dart';
|
||||||
|
import 'package:sk_base_mobile/models/file.model.dart';
|
||||||
|
import 'package:sk_base_mobile/util/screen_adaper_util.dart';
|
||||||
|
import 'package:sk_base_mobile/widgets/fade_in_cache_image.dart';
|
||||||
|
import 'package:sk_base_mobile/widgets/loading_indicator.dart';
|
||||||
|
|
||||||
|
class ImagePreivew extends StatefulWidget {
|
||||||
|
ImagePreivew({
|
||||||
|
super.key,
|
||||||
|
required this.galleryItems,
|
||||||
|
this.backgroundDecoration,
|
||||||
|
this.minScale,
|
||||||
|
this.maxScale,
|
||||||
|
this.initialIndex = 0,
|
||||||
|
this.scrollDirection = Axis.horizontal,
|
||||||
|
}) : pageController = PageController(initialPage: initialIndex);
|
||||||
|
final BoxDecoration? backgroundDecoration;
|
||||||
|
final dynamic minScale;
|
||||||
|
final dynamic maxScale;
|
||||||
|
final int initialIndex;
|
||||||
|
final PageController pageController;
|
||||||
|
final List<FileModel> galleryItems;
|
||||||
|
final Axis scrollDirection;
|
||||||
|
@override
|
||||||
|
State<ImagePreivew> createState() => _ImagePreivewState();
|
||||||
|
}
|
||||||
|
|
||||||
|
class _ImagePreivewState extends State<ImagePreivew> {
|
||||||
|
late int currentIndex = widget.initialIndex;
|
||||||
|
@override
|
||||||
|
Widget build(BuildContext context) {
|
||||||
|
return Container(
|
||||||
|
decoration: widget.backgroundDecoration,
|
||||||
|
constraints: BoxConstraints.expand(
|
||||||
|
height: MediaQuery.of(context).size.height,
|
||||||
|
),
|
||||||
|
child: Stack(
|
||||||
|
alignment: Alignment.bottomRight,
|
||||||
|
children: <Widget>[
|
||||||
|
PhotoViewGallery.builder(
|
||||||
|
scrollPhysics: const BouncingScrollPhysics(),
|
||||||
|
builder: _buildItem,
|
||||||
|
itemCount: widget.galleryItems.length,
|
||||||
|
loadingBuilder: (_, _1) => const LoadingIndicator(common: true),
|
||||||
|
backgroundDecoration: widget.backgroundDecoration,
|
||||||
|
pageController: widget.pageController,
|
||||||
|
onPageChanged: onPageChanged,
|
||||||
|
scrollDirection: widget.scrollDirection,
|
||||||
|
),
|
||||||
|
Container(
|
||||||
|
padding: const EdgeInsets.all(20.0),
|
||||||
|
child: Text(
|
||||||
|
"照片 ${currentIndex + 1}",
|
||||||
|
style: TextStyle(
|
||||||
|
decoration: TextDecoration.none,
|
||||||
|
color: Colors.white,
|
||||||
|
fontSize: ScreenAdaper.sp(20),
|
||||||
|
),
|
||||||
|
),
|
||||||
|
)
|
||||||
|
],
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
PhotoViewGalleryPageOptions _buildItem(BuildContext context, int index) {
|
||||||
|
final FileModel item = widget.galleryItems[index];
|
||||||
|
return PhotoViewGalleryPageOptions(
|
||||||
|
onTapUp: (_, _1, _2) {
|
||||||
|
Get.back();
|
||||||
|
},
|
||||||
|
imageProvider: Image.network('${GloablConfig.OSS_URL}${item.path}').image,
|
||||||
|
initialScale: PhotoViewComputedScale.contained,
|
||||||
|
minScale: PhotoViewComputedScale.contained * (0.5 + index / 10),
|
||||||
|
maxScale: PhotoViewComputedScale.covered * 4.1,
|
||||||
|
heroAttributes: PhotoViewHeroAttributes(tag: '${item.id}'),
|
||||||
|
);
|
||||||
|
// return item.isSvg
|
||||||
|
// ? PhotoViewGalleryPageOptions.customChild(
|
||||||
|
// child: Container(
|
||||||
|
// width: 300,
|
||||||
|
// height: 300,
|
||||||
|
// child: SvgPicture.asset(
|
||||||
|
// item.resource,
|
||||||
|
// height: 200.0,
|
||||||
|
// ),
|
||||||
|
// ),
|
||||||
|
// childSize: const Size(300, 300),
|
||||||
|
// initialScale: PhotoViewComputedScale.contained,
|
||||||
|
// minScale: PhotoViewComputedScale.contained * (0.5 + index / 10),
|
||||||
|
// maxScale: PhotoViewComputedScale.covered * 4.1,
|
||||||
|
// heroAttributes: PhotoViewHeroAttributes(tag: item.id),
|
||||||
|
// )
|
||||||
|
// : PhotoViewGalleryPageOptions(
|
||||||
|
// imageProvider: AssetImage(item.resource),
|
||||||
|
// initialScale: PhotoViewComputedScale.contained,
|
||||||
|
// minScale: PhotoViewComputedScale.contained * (0.5 + index / 10),
|
||||||
|
// maxScale: PhotoViewComputedScale.covered * 4.1,
|
||||||
|
// heroAttributes: PhotoViewHeroAttributes(tag: item.id),
|
||||||
|
// );
|
||||||
|
}
|
||||||
|
|
||||||
|
void onPageChanged(int index) {
|
||||||
|
setState(() {
|
||||||
|
currentIndex = index;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
|
@ -1,17 +1,23 @@
|
||||||
import 'package:flutter/cupertino.dart';
|
import 'package:flutter/cupertino.dart';
|
||||||
|
import 'package:loading_animation_widget/loading_animation_widget.dart';
|
||||||
import 'package:sk_base_mobile/app_theme.dart';
|
import 'package:sk_base_mobile/app_theme.dart';
|
||||||
import 'package:sk_base_mobile/util/screen_adaper_util.dart';
|
import 'package:sk_base_mobile/util/screen_adaper_util.dart';
|
||||||
|
|
||||||
class LoadingIndicator extends StatelessWidget {
|
class LoadingIndicator extends StatelessWidget {
|
||||||
final bool animating;
|
final bool animating;
|
||||||
const LoadingIndicator({super.key, this.animating = true});
|
final bool common;
|
||||||
|
const LoadingIndicator(
|
||||||
|
{super.key, this.animating = true, this.common = false});
|
||||||
|
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
return CupertinoActivityIndicator(
|
return common
|
||||||
animating: animating,
|
? LoadingAnimationWidget.fourRotatingDots(
|
||||||
color: AppTheme.primaryColor,
|
color: AppTheme.primaryColorLight, size: ScreenAdaper.sp(40))
|
||||||
radius: ScreenAdaper.sp(20),
|
: CupertinoActivityIndicator(
|
||||||
);
|
animating: animating,
|
||||||
|
color: AppTheme.primaryColor,
|
||||||
|
radius: ScreenAdaper.sp(20),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
import 'dart:io';
|
import 'dart:io';
|
||||||
import 'package:sk_base_mobile/apis/api.dart' as Api;
|
import 'package:sk_base_mobile/apis/index.dart';
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:get/get.dart';
|
import 'package:get/get.dart';
|
||||||
import 'package:image_picker/image_picker.dart';
|
import 'package:image_picker/image_picker.dart';
|
||||||
|
|
16
pubspec.lock
16
pubspec.lock
|
@ -416,6 +416,14 @@ packages:
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "4.1.7"
|
version: "4.1.7"
|
||||||
|
image_gallery_saver:
|
||||||
|
dependency: "direct main"
|
||||||
|
description:
|
||||||
|
name: image_gallery_saver
|
||||||
|
sha256: "0aba74216a4d9b0561510cb968015d56b701ba1bd94aace26aacdd8ae5761816"
|
||||||
|
url: "https://pub.dev"
|
||||||
|
source: hosted
|
||||||
|
version: "2.0.3"
|
||||||
image_picker:
|
image_picker:
|
||||||
dependency: "direct main"
|
dependency: "direct main"
|
||||||
description:
|
description:
|
||||||
|
@ -680,6 +688,14 @@ packages:
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "6.0.2"
|
version: "6.0.2"
|
||||||
|
photo_view:
|
||||||
|
dependency: "direct main"
|
||||||
|
description:
|
||||||
|
name: photo_view
|
||||||
|
sha256: "8036802a00bae2a78fc197af8a158e3e2f7b500561ed23b4c458107685e645bb"
|
||||||
|
url: "https://pub.dev"
|
||||||
|
source: hosted
|
||||||
|
version: "0.14.0"
|
||||||
platform:
|
platform:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
|
|
|
@ -58,6 +58,8 @@ dependencies:
|
||||||
path_provider: ^2.1.2
|
path_provider: ^2.1.2
|
||||||
flutter_typeahead: ^5.2.0
|
flutter_typeahead: ^5.2.0
|
||||||
decimal: ^2.3.3
|
decimal: ^2.3.3
|
||||||
|
photo_view: ^0.14.0
|
||||||
|
image_gallery_saver: ^2.0.3
|
||||||
|
|
||||||
|
|
||||||
dev_dependencies:
|
dev_dependencies:
|
||||||
|
|
Loading…
Reference in New Issue