ui render

null-safety-migration
suvaissov 2021-05-13 21:04:56 +06:00
parent 8a7e606be1
commit c7ce34407e
6 changed files with 162 additions and 55 deletions

View File

@ -8,6 +8,7 @@ class ProductDao {
String eanCode; String eanCode;
int article; int article;
String excise; String excise;
int transactionId;
Map<String, dynamic> toMap() { Map<String, dynamic> toMap() {
@ -21,6 +22,7 @@ class ProductDao {
'eanCode': eanCode, 'eanCode': eanCode,
'article': article, 'article': article,
'excise': excise, 'excise': excise,
'transactionId' : transactionId,
}; };
return map; return map;
} }
@ -37,6 +39,7 @@ class ProductDao {
eanCode = map['eanCode']; eanCode = map['eanCode'];
article = map['article']; article = map['article'];
excise = map['excise']; excise = map['excise'];
transactionId = map['transactionId'];
} }
} }

View File

@ -76,6 +76,7 @@ ThunkAction<AppState> addSellItem({Good good, String excise}) {
if (set.isNotEmpty) { if (set.isNotEmpty) {
Category category = Category.fromMap(set.first); Category category = Category.fromMap(set.first);
item.categoryId = category.id; item.categoryId = category.id;
item.categoryName = category.name;
} }
} }
@ -99,8 +100,55 @@ ThunkAction<AppState> addSellItem({Good good, String excise}) {
}; };
} }
ThunkAction<AppState> removeSellItem({int transactionId}) {
return (Store<AppState> store) async {
int appCompanyId = store.state.userState.auth.companyId;
String uuid = store.state.sellState.transactionState.uuid;
int count = await _dbService.delete(TransactionTableName, transactionId);
log.i('removeSellItem ${count} by transactionId:${transactionId}');
// List<Map<String, dynamic>> set = await _dbService.queryRowsWithWhere(
// TransactionTableName,
// '$TransactionColumnId = ? ',
// [transactionId]);
// if (set.isNotEmpty) {
// for (Map<String, dynamic> map in set) {
// Transaction _transaction = Transaction.fromMap(map);
// ProductDao _product = ProductDao.fromMap(jsonDecode(_transaction.data));
// if (_product.id == good.id && _product.excise == excise) {
// transaction = _transaction;
// break;
// }
// }
// }
// refresh from db ? after save data
await loadSellData(store);
};
}
Future<void> removeAllSellData(Store<AppState> store) async {
try {
log.i('removeAllSellData');
int appCompanyId = store.state.userState.auth.companyId;
String uuid = store.state.sellState.transactionState.uuid;
await _dbService.deleteByWhere(
TransactionTableName,
'$TransactionColumnAppCompanyId = ? '
' and $TransactionColumnStatus = ? '
' and ${TransactionColumnType} = ?'
' and ${TransactionColumnUuid} = ?',
[appCompanyId, TransactionStatusPrepare, TransactionTypeSell, uuid]);
await loadSellData(store);
} catch (e, stack) {
log.e('removeAllSellData', e, stack);
}
}
Future<void> loadSellData(Store<AppState> store) async { Future<void> loadSellData(Store<AppState> store) async {
try { try {
log.i('loadSellData');
int appCompanyId = store.state.userState.auth.companyId; int appCompanyId = store.state.userState.auth.companyId;
List<Map<String, dynamic>> set = await _dbService.queryRowsWithWhere( List<Map<String, dynamic>> set = await _dbService.queryRowsWithWhere(
TransactionTableName, TransactionTableName,
@ -112,7 +160,9 @@ Future<void> loadSellData(Store<AppState> store) async {
for (Map<String, dynamic> map in set) { for (Map<String, dynamic> map in set) {
Transaction transaction = Transaction.fromMap(map); Transaction transaction = Transaction.fromMap(map);
uuid = transaction.uuid; uuid = transaction.uuid;
list.add(ProductDao.fromMap(jsonDecode(transaction.data))); ProductDao productDao = ProductDao.fromMap(jsonDecode(transaction.data));
productDao.transactionId = transaction.id;
list.add(productDao);
} }
store.dispatch(SetSellStateAction(SellState(items: list, transactionState: TransactionState()..uuid = uuid))); store.dispatch(SetSellStateAction(SellState(items: list, transactionState: TransactionState()..uuid = uuid)));
} catch (e, stack) { } catch (e, stack) {

View File

@ -144,5 +144,10 @@ class DbService extends BaseService {
return await db.delete(table); return await db.delete(table);
} }
Future<int> deleteByWhere(String table, String where, List<dynamic> args) async {
Database db = await instance.database;
return await db.delete(table, where: where, whereArgs: args);
}
Future close() async => instance.close(); Future close() async => instance.close();
} }

View File

@ -1,5 +1,7 @@
import 'package:flutter/cupertino.dart'; import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:satu/core/redux/actions/sell_actions.dart';
import 'package:satu/core/redux/store.dart';
import 'package:satu/shared/app_colors.dart'; import 'package:satu/shared/app_colors.dart';
import 'package:satu/shared/shared_styles.dart'; import 'package:satu/shared/shared_styles.dart';
import 'package:satu/shared/ui_helpers.dart'; import 'package:satu/shared/ui_helpers.dart';
@ -11,8 +13,9 @@ class ProductListItem extends StatelessWidget {
final num price; final num price;
final num count; final num count;
final bool isOdd; final bool isOdd;
final int transactionId;
const ProductListItem({Key key, this.name, this.ean, this.categoryName, this.price, this.count, this.isOdd}) : super(key: key); const ProductListItem({Key key, this.name, this.ean, this.categoryName, this.price, this.count, this.isOdd, this.transactionId}) : super(key: key);
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {
@ -27,16 +30,16 @@ class ProductListItem extends StatelessWidget {
context: context, context: context,
builder: (BuildContext context) { builder: (BuildContext context) {
return AlertDialog( return AlertDialog(
title: const Text("Confirm"), title: const Text("Внимание"),
content: const Text("Are you sure you wish to delete this item?"), content: Text("Удалить товар \"${this.name}\" - ${count} ед. ?"),
actions: <Widget>[ actions: <Widget>[
FlatButton( FlatButton(
onPressed: () => Navigator.of(context).pop(true), onPressed: () => Navigator.of(context).pop(true),
child: const Text("DELETE") child: const Text("Удалить")
), ),
FlatButton( FlatButton(
onPressed: () => Navigator.of(context).pop(false), onPressed: () => Navigator.of(context).pop(false),
child: const Text("CANCEL"), child: const Text("Отмена"),
), ),
], ],
); );
@ -45,6 +48,7 @@ class ProductListItem extends StatelessWidget {
}, },
onDismissed: (direction) { onDismissed: (direction) {
print(direction); print(direction);
Redux.store.dispatch(removeSellItem( transactionId: this.transactionId ));
}, },
key: Key(name), key: Key(name),
child: ListTile( child: ListTile(
@ -63,7 +67,7 @@ class ProductListItem extends StatelessWidget {
Text(name , style: const TextStyle( fontWeight: FontWeight.w500 ), overflow: TextOverflow.ellipsis, maxLines: 2,), Text(name , style: const TextStyle( fontWeight: FontWeight.w500 ), overflow: TextOverflow.ellipsis, maxLines: 2,),
verticalSpaceTiny, verticalSpaceTiny,
Text('Штрих-код: $ean' , style: productSubTextStyle,), Text('Штрих-код: $ean' , style: productSubTextStyle,),
Text(categoryName, style: productSubTextStyle,) Text(categoryName ?? '', style: productSubTextStyle,)
], ],
), ),
), ),

View File

@ -1,12 +1,16 @@
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flutter_redux/flutter_redux.dart'; import 'package:flutter_redux/flutter_redux.dart';
import 'package:flutter_screenutil/flutter_screenutil.dart';
import 'package:satu/core/models/flow/product_dao.dart'; import 'package:satu/core/models/flow/product_dao.dart';
import 'package:satu/core/redux/actions/sell_actions.dart';
import 'package:satu/core/redux/state/sell_state.dart'; import 'package:satu/core/redux/state/sell_state.dart';
import 'package:satu/core/redux/store.dart'; import 'package:satu/core/redux/store.dart';
import 'package:satu/core/services/navigator_service.dart'; import 'package:satu/core/services/navigator_service.dart';
import 'package:satu/core/utils/locator.dart'; import 'package:satu/core/utils/locator.dart';
import 'package:satu/routes/route_names.dart'; import 'package:satu/routes/route_names.dart';
import 'package:satu/shared/app_colors.dart'; import 'package:satu/shared/app_colors.dart';
import 'package:satu/shared/ui_helpers.dart';
import 'package:satu/views/work/tabs/component/product_list_item.dart'; import 'package:satu/views/work/tabs/component/product_list_item.dart';
import 'package:satu/views/work/tabs/component/products_app_bar.dart'; import 'package:satu/views/work/tabs/component/products_app_bar.dart';
import 'package:satu/views/work/tabs/component/products_header_bar.dart'; import 'package:satu/views/work/tabs/component/products_header_bar.dart';
@ -16,45 +20,85 @@ class SellView extends StatelessWidget {
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {
return StoreConnector<AppState, SellState>( return StoreConnector<AppState, SellState>(
converter: (store) => store.state.sellState, converter: (store) => store.state.sellState,
builder: (_, state) { builder: (_, state) {
return Scaffold( return Scaffold(
appBar: ProductsAppBar( appBar: ProductsAppBar(
title: 'Продажа', title: 'Продажа',
actions: actions(), actions: actions(),
elevation: 2.0, elevation: 2.0,
child: ProductHeaderBar( child: ProductHeaderBar(
count: state.items.length, count: state.items.length,
sum: sumProducts(state.items), sum: sumProducts(state.items),
),
backgroundColor: backgroundColor,
childHeight: 80,
),
body: Column(
children: [
//ProductHeaderBar(count: 14, sum: 25000,),
Expanded(
child: ListView.builder(
physics: BouncingScrollPhysics(),
itemCount: state.items.length,
itemBuilder: (BuildContext context, int index) {
ProductDao product = state.items.elementAt(index);
return ProductListItem(
ean: product.eanCode,
isOdd: index % 2 == 0,
name: product.productName,
price: product.price,
count: product.count,
categoryName: product.productName,
);
},
),
), ),
], backgroundColor: backgroundColor,
), childHeight: 80,
); ),
} body: ListView.builder(
); physics: BouncingScrollPhysics(),
itemCount: state.items.length,
itemBuilder: (BuildContext context, int index) {
ProductDao product = state.items.elementAt(index);
return ProductListItem(
key: UniqueKey(),
ean: product.eanCode,
isOdd: index % 2 == 0,
name: product.productName,
price: product.price,
count: product.count,
categoryName: product.categoryName,
transactionId: product.transactionId,
);
},
),
floatingActionButtonLocation: FloatingActionButtonLocation.centerDocked,
floatingActionButton: floatingActionButtonRender(),
);
});
}
Widget floatingActionButtonRender() {
return StoreConnector<AppState, SellState>(
converter: (store) => store.state.sellState,
builder: (_, snapshot) {
return Padding(
padding: const EdgeInsets.symmetric(horizontal: 12.0, vertical: 16.0),
child: Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
crossAxisAlignment: CrossAxisAlignment.end,
children: <Widget>[
Visibility(
visible: snapshot.items.isNotEmpty,
child: FloatingActionButton(
elevation: 2,
backgroundColor: greenColor,
onPressed: () => print('check'),
child: Icon(
Icons.check,
color: whiteColor,
size: 30.sp
),
)),
Column(
mainAxisAlignment: MainAxisAlignment.end,
children: [
FloatingActionButton(
elevation: 2,
onPressed: () => locator<NavigatorService>().push(AddProductViewRoute),
child: Icon(Icons.add, size: 30.sp,),
),
verticalSpaceMedium,
FloatingActionButton(
elevation: 2,
onPressed: () => locator<NavigatorService>().push(AddByBarcodeViewRoute),
child: Icon(Icons.qr_code_rounded, size: 30.sp),
),
],
)
],
),
);
});
} }
List<Widget> actions() { List<Widget> actions() {
@ -62,17 +106,9 @@ class SellView extends StatelessWidget {
Padding( Padding(
padding: const EdgeInsets.all(8.0), padding: const EdgeInsets.all(8.0),
child: IconButton( child: IconButton(
icon: Icon(Icons.add_box, size: 30.0, color: yellowColor), icon: Icon(Icons.delete, size: 30.0, color: yellowColor),
onPressed: () { onPressed: () {
locator<NavigatorService>().push(AddProductViewRoute); Redux.store.dispatch(removeAllSellData);
}),
),
Padding(
padding: const EdgeInsets.all(8.0),
child: IconButton(
icon: Icon(Icons.camera_enhance_rounded, size: 30.0, color: yellowColor),
onPressed: () {
locator<NavigatorService>().push(AddByBarcodeViewRoute);
}), }),
) )
]; ];

View File

@ -1,5 +1,7 @@
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:material_design_icons_flutter/material_design_icons_flutter.dart'; import 'package:material_design_icons_flutter/material_design_icons_flutter.dart';
import 'package:satu/core/redux/actions/sell_actions.dart';
import 'package:satu/core/redux/store.dart';
import 'package:satu/shared/app_colors.dart'; import 'package:satu/shared/app_colors.dart';
import 'package:satu/views/work/tabs/buy_view.dart'; import 'package:satu/views/work/tabs/buy_view.dart';
import 'package:satu/views/work/tabs/journal_view.dart'; import 'package:satu/views/work/tabs/journal_view.dart';
@ -24,6 +26,13 @@ class _WorkViewState extends State<WorkView> {
]; ];
@override
void initState() {
super.initState();
// state sell view
Redux.store.dispatch(loadSellData);
}
void _onItemTapped(int index) { void _onItemTapped(int index) {
setState(() { setState(() {
_selectedIndex = index; _selectedIndex = index;