496 lines
12 KiB
Dart
496 lines
12 KiB
Dart
import 'dart:async';
|
|
|
|
import 'package:built_collection/built_collection.dart';
|
|
import 'package:flutter/material.dart';
|
|
import 'package:flutter/widgets.dart';
|
|
import 'package:flutter_redux/flutter_redux.dart';
|
|
import 'package:invoiceninja_flutter/data/models/models.dart';
|
|
import 'package:invoiceninja_flutter/redux/app/app_actions.dart';
|
|
import 'package:invoiceninja_flutter/redux/app/app_state.dart';
|
|
import 'package:invoiceninja_flutter/utils/completers.dart';
|
|
import 'package:invoiceninja_flutter/utils/localization.dart';
|
|
import 'package:invoiceninja_flutter/utils/pdf.dart';
|
|
import 'package:url_launcher/url_launcher.dart';
|
|
|
|
class ViewCreditList extends AbstractNavigatorAction
|
|
implements PersistUI, StopLoading {
|
|
ViewCreditList({@required NavigatorState navigator, this.force = false})
|
|
: super(navigator: navigator);
|
|
|
|
final bool force;
|
|
}
|
|
|
|
class ViewCredit extends AbstractNavigatorAction
|
|
implements PersistUI, PersistPrefs {
|
|
ViewCredit({
|
|
this.creditId,
|
|
@required NavigatorState navigator,
|
|
this.force = false,
|
|
}) : super(navigator: navigator);
|
|
|
|
final String creditId;
|
|
final bool force;
|
|
}
|
|
|
|
class EditCredit extends AbstractNavigatorAction
|
|
implements PersistUI, PersistPrefs {
|
|
EditCredit(
|
|
{this.credit,
|
|
@required NavigatorState navigator,
|
|
this.creditItemIndex,
|
|
this.completer,
|
|
this.force = false})
|
|
: super(navigator: navigator);
|
|
|
|
final InvoiceEntity credit;
|
|
final int creditItemIndex;
|
|
final Completer completer;
|
|
final bool force;
|
|
}
|
|
|
|
class ShowEmailCredit {
|
|
ShowEmailCredit({this.credit, this.context, this.completer});
|
|
|
|
final InvoiceEntity credit;
|
|
final BuildContext context;
|
|
final Completer completer;
|
|
}
|
|
|
|
class EditCreditItem implements PersistUI {
|
|
EditCreditItem([this.creditItemIndex]);
|
|
|
|
final int creditItemIndex;
|
|
}
|
|
|
|
class UpdateCredit implements PersistUI {
|
|
UpdateCredit(this.credit);
|
|
|
|
final InvoiceEntity credit;
|
|
}
|
|
|
|
class UpdateCreditClient implements PersistUI {
|
|
UpdateCreditClient({this.client});
|
|
|
|
final ClientEntity client;
|
|
}
|
|
|
|
class LoadCredit {
|
|
LoadCredit({this.completer, this.creditId});
|
|
|
|
final Completer completer;
|
|
final String creditId;
|
|
}
|
|
|
|
class LoadCredits {
|
|
LoadCredits({this.completer});
|
|
|
|
final Completer completer;
|
|
}
|
|
|
|
class LoadCreditRequest implements StartLoading {}
|
|
|
|
class LoadCreditFailure implements StopLoading {
|
|
LoadCreditFailure(this.error);
|
|
|
|
final dynamic error;
|
|
|
|
@override
|
|
String toString() {
|
|
return 'LoadCreditFailure{error: $error}';
|
|
}
|
|
}
|
|
|
|
class LoadCreditSuccess implements StopLoading, PersistData {
|
|
LoadCreditSuccess(this.credit);
|
|
|
|
final InvoiceEntity credit;
|
|
|
|
@override
|
|
String toString() {
|
|
return 'LoadCreditSuccess{credit: $credit}';
|
|
}
|
|
}
|
|
|
|
class LoadCreditsRequest implements StartLoading {}
|
|
|
|
class LoadCreditsFailure implements StopLoading {
|
|
LoadCreditsFailure(this.error);
|
|
|
|
final dynamic error;
|
|
|
|
@override
|
|
String toString() {
|
|
return 'LoadCreditsFailure{error: $error}';
|
|
}
|
|
}
|
|
|
|
class LoadCreditsSuccess implements StopLoading, PersistData {
|
|
LoadCreditsSuccess(this.credits);
|
|
|
|
final BuiltList<InvoiceEntity> credits;
|
|
|
|
@override
|
|
String toString() {
|
|
return 'LoadCreditsSuccess{credits: $credits}';
|
|
}
|
|
}
|
|
|
|
class AddCreditContact implements PersistUI {
|
|
AddCreditContact({this.contact, this.invitation});
|
|
|
|
final ContactEntity contact;
|
|
final InvitationEntity invitation;
|
|
}
|
|
|
|
class RemoveCreditContact implements PersistUI {
|
|
RemoveCreditContact({this.invitation});
|
|
|
|
final InvitationEntity invitation;
|
|
}
|
|
|
|
class AddCreditItem implements PersistUI {
|
|
AddCreditItem({this.creditItem});
|
|
|
|
final InvoiceItemEntity creditItem;
|
|
}
|
|
|
|
class AddCreditItems implements PersistUI {
|
|
AddCreditItems(this.creditItems);
|
|
|
|
final List<InvoiceItemEntity> creditItems;
|
|
}
|
|
|
|
class UpdateCreditItem implements PersistUI {
|
|
UpdateCreditItem({this.index, this.creditItem});
|
|
|
|
final int index;
|
|
final InvoiceItemEntity creditItem;
|
|
}
|
|
|
|
class DeleteCreditItem implements PersistUI {
|
|
DeleteCreditItem(this.index);
|
|
|
|
final int index;
|
|
}
|
|
|
|
class SaveCreditRequest implements StartSaving {
|
|
SaveCreditRequest({this.completer, this.credit});
|
|
|
|
final Completer completer;
|
|
final InvoiceEntity credit;
|
|
}
|
|
|
|
class SaveCreditSuccess implements StopSaving, PersistData, PersistUI {
|
|
SaveCreditSuccess(this.credit);
|
|
|
|
final InvoiceEntity credit;
|
|
}
|
|
|
|
class AddCreditSuccess implements StopSaving, PersistData, PersistUI {
|
|
AddCreditSuccess(this.credit);
|
|
|
|
final InvoiceEntity credit;
|
|
}
|
|
|
|
class SaveCreditFailure implements StopSaving {
|
|
SaveCreditFailure(this.error);
|
|
|
|
final Object error;
|
|
}
|
|
|
|
class EmailCreditRequest implements StartSaving {
|
|
EmailCreditRequest(
|
|
{this.completer, this.creditId, this.template, this.subject, this.body});
|
|
|
|
final Completer completer;
|
|
final String creditId;
|
|
final EmailTemplate template;
|
|
final String subject;
|
|
final String body;
|
|
}
|
|
|
|
class EmailCreditSuccess implements StopSaving, PersistData {}
|
|
|
|
class EmailCreditFailure implements StopSaving {
|
|
EmailCreditFailure(this.error);
|
|
|
|
final dynamic error;
|
|
}
|
|
|
|
class MarkSentCreditRequest implements StartSaving {
|
|
MarkSentCreditRequest(this.completer, this.creditIds);
|
|
|
|
final Completer completer;
|
|
final List<String> creditIds;
|
|
}
|
|
|
|
class MarkSentCreditSuccess implements StopSaving, PersistData {
|
|
MarkSentCreditSuccess(this.credits);
|
|
|
|
final List<InvoiceEntity> credits;
|
|
}
|
|
|
|
class MarkSentCreditFailure implements StopSaving {
|
|
MarkSentCreditFailure(this.error);
|
|
|
|
final Object error;
|
|
}
|
|
|
|
class ArchiveCreditsRequest implements StartSaving {
|
|
ArchiveCreditsRequest(this.completer, this.creditIds);
|
|
|
|
final Completer completer;
|
|
|
|
final List<String> creditIds;
|
|
}
|
|
|
|
class ArchiveCreditsSuccess implements StopSaving, PersistData {
|
|
ArchiveCreditsSuccess(this.credits);
|
|
|
|
final List<InvoiceEntity> credits;
|
|
}
|
|
|
|
class ArchiveCreditsFailure implements StopSaving {
|
|
ArchiveCreditsFailure(this.credits);
|
|
|
|
final List<InvoiceEntity> credits;
|
|
}
|
|
|
|
class DeleteCreditsRequest implements StartSaving {
|
|
DeleteCreditsRequest(this.completer, this.creditIds);
|
|
|
|
final Completer completer;
|
|
|
|
final List<String> creditIds;
|
|
}
|
|
|
|
class DeleteCreditsSuccess implements StopSaving, PersistData {
|
|
DeleteCreditsSuccess(this.credits);
|
|
|
|
final List<InvoiceEntity> credits;
|
|
}
|
|
|
|
class DeleteCreditsFailure implements StopSaving {
|
|
DeleteCreditsFailure(this.credits);
|
|
|
|
final List<InvoiceEntity> credits;
|
|
}
|
|
|
|
class RestoreCreditsRequest implements StartSaving {
|
|
RestoreCreditsRequest(this.completer, this.creditIds);
|
|
|
|
final Completer completer;
|
|
|
|
final List<String> creditIds;
|
|
}
|
|
|
|
class RestoreCreditsSuccess implements StopSaving, PersistData {
|
|
RestoreCreditsSuccess(this.credits);
|
|
|
|
final List<InvoiceEntity> credits;
|
|
}
|
|
|
|
class RestoreCreditsFailure implements StopSaving {
|
|
RestoreCreditsFailure(this.credits);
|
|
|
|
final List<InvoiceEntity> credits;
|
|
}
|
|
|
|
class FilterCredits implements PersistUI {
|
|
FilterCredits(this.filter);
|
|
|
|
final String filter;
|
|
}
|
|
|
|
class SortCredits implements PersistUI {
|
|
SortCredits(this.field);
|
|
|
|
final String field;
|
|
}
|
|
|
|
class FilterCreditsByState implements PersistUI {
|
|
FilterCreditsByState(this.state);
|
|
|
|
final EntityState state;
|
|
}
|
|
|
|
class FilterCreditsByStatus implements PersistUI {
|
|
FilterCreditsByStatus(this.status);
|
|
|
|
final EntityStatus status;
|
|
}
|
|
|
|
class FilterCreditDropdown {
|
|
FilterCreditDropdown(this.filter);
|
|
|
|
final String filter;
|
|
}
|
|
|
|
class FilterCreditsByCustom1 implements PersistUI {
|
|
FilterCreditsByCustom1(this.value);
|
|
|
|
final String value;
|
|
}
|
|
|
|
class FilterCreditsByCustom2 implements PersistUI {
|
|
FilterCreditsByCustom2(this.value);
|
|
|
|
final String value;
|
|
}
|
|
|
|
class FilterCreditsByCustom3 implements PersistUI {
|
|
FilterCreditsByCustom3(this.value);
|
|
|
|
final String value;
|
|
}
|
|
|
|
class FilterCreditsByCustom4 implements PersistUI {
|
|
FilterCreditsByCustom4(this.value);
|
|
|
|
final String value;
|
|
}
|
|
|
|
class SaveCreditDocumentRequest implements StartSaving {
|
|
SaveCreditDocumentRequest({
|
|
@required this.completer,
|
|
@required this.filePath,
|
|
@required this.credit,
|
|
});
|
|
|
|
final Completer completer;
|
|
final String filePath;
|
|
final InvoiceEntity credit;
|
|
}
|
|
|
|
class SaveCreditDocumentSuccess implements StopSaving, PersistData, PersistUI {
|
|
SaveCreditDocumentSuccess(this.document);
|
|
|
|
final DocumentEntity document;
|
|
}
|
|
|
|
class SaveCreditDocumentFailure implements StopSaving {
|
|
SaveCreditDocumentFailure(this.error);
|
|
|
|
final Object error;
|
|
}
|
|
|
|
Future handleCreditAction(
|
|
BuildContext context, List<BaseEntity> credits, EntityAction action) async {
|
|
assert(
|
|
[
|
|
EntityAction.restore,
|
|
EntityAction.archive,
|
|
EntityAction.delete,
|
|
EntityAction.toggleMultiselect
|
|
].contains(action) ||
|
|
credits.length == 1,
|
|
'Cannot perform this action on more than one credit');
|
|
|
|
final store = StoreProvider.of<AppState>(context);
|
|
final state = store.state;
|
|
final localization = AppLocalization.of(context);
|
|
final credit = credits.first as InvoiceEntity;
|
|
final creditIds = credits.map((credit) => credit.id).toList();
|
|
|
|
switch (action) {
|
|
case EntityAction.edit:
|
|
editEntity(context: context, entity: credit);
|
|
break;
|
|
case EntityAction.viewPdf:
|
|
viewPdf(credit, context);
|
|
break;
|
|
case EntityAction.clientPortal:
|
|
if (await canLaunch(credit.invitationSilentLink)) {
|
|
await launch(credit.invitationSilentLink,
|
|
forceSafariVC: false, forceWebView: false);
|
|
}
|
|
break;
|
|
case EntityAction.viewInvoice:
|
|
viewEntityById(
|
|
context: context,
|
|
// TODO fix this
|
|
// entityId: credit.creditInvoiceId,
|
|
entityType: EntityType.invoice);
|
|
break;
|
|
case EntityAction.markSent:
|
|
store.dispatch(MarkSentCreditRequest(
|
|
snackBarCompleter<Null>(context, localization.markedCreditAsSent),
|
|
creditIds));
|
|
break;
|
|
case EntityAction.emailCredit:
|
|
store.dispatch(ShowEmailCredit(
|
|
completer:
|
|
snackBarCompleter<Null>(context, localization.emailedCredit),
|
|
credit: credit,
|
|
context: context));
|
|
break;
|
|
case EntityAction.cloneToInvoice:
|
|
createEntity(context: context, entity: credit.clone);
|
|
break;
|
|
case EntityAction.cloneToCredit:
|
|
createEntity(context: context, entity: credit.clone);
|
|
createEntity(context: context, entity: credit.clone);
|
|
break;
|
|
case EntityAction.newPayment:
|
|
createEntity(
|
|
context: context,
|
|
entity: PaymentEntity(state: state).rebuild((b) => b
|
|
..isForCredit = true
|
|
..clientId = credit.clientId
|
|
..credits.addAll(credits
|
|
.map((credit) => PaymentableEntity.fromCredit(credit))
|
|
.toList())),
|
|
filterEntity: state.clientState.map[credit.clientId],
|
|
);
|
|
break;
|
|
case EntityAction.restore:
|
|
store.dispatch(RestoreCreditsRequest(
|
|
snackBarCompleter<Null>(context, localization.restoredCredit),
|
|
creditIds));
|
|
break;
|
|
case EntityAction.archive:
|
|
store.dispatch(ArchiveCreditsRequest(
|
|
snackBarCompleter<Null>(context, localization.archivedCredit),
|
|
creditIds));
|
|
break;
|
|
case EntityAction.delete:
|
|
store.dispatch(DeleteCreditsRequest(
|
|
snackBarCompleter<Null>(context, localization.deletedCredit),
|
|
creditIds));
|
|
break;
|
|
case EntityAction.toggleMultiselect:
|
|
if (!store.state.creditListState.isInMultiselect()) {
|
|
store.dispatch(StartCreditMultiselect());
|
|
}
|
|
|
|
if (credits.isEmpty) {
|
|
break;
|
|
}
|
|
|
|
for (final credit in credits) {
|
|
if (!store.state.creditListState.isSelected(credit.id)) {
|
|
store.dispatch(AddToCreditMultiselect(entity: credit));
|
|
} else {
|
|
store.dispatch(RemoveFromCreditMultiselect(entity: credit));
|
|
}
|
|
}
|
|
break;
|
|
}
|
|
}
|
|
|
|
class StartCreditMultiselect {}
|
|
|
|
class AddToCreditMultiselect {
|
|
AddToCreditMultiselect({@required this.entity});
|
|
|
|
final BaseEntity entity;
|
|
}
|
|
|
|
class RemoveFromCreditMultiselect {
|
|
RemoveFromCreditMultiselect({@required this.entity});
|
|
|
|
final BaseEntity entity;
|
|
}
|
|
|
|
class ClearCreditMultiselect {}
|