feat: create customer
This commit is contained in:
parent
52bedee66d
commit
c87276a0ea
@ -102,9 +102,11 @@ class CustomModalDialog extends StatelessWidget {
|
||||
],
|
||||
),
|
||||
),
|
||||
Padding(
|
||||
padding: contentPadding ?? EdgeInsets.zero,
|
||||
child: child,
|
||||
Flexible(
|
||||
child: SingleChildScrollView(
|
||||
padding: contentPadding ?? EdgeInsets.zero,
|
||||
child: child,
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
|
||||
@ -14,6 +14,8 @@ class CustomTextField extends StatelessWidget {
|
||||
final Widget? prefixIcon;
|
||||
final Widget? suffixIcon;
|
||||
final bool readOnly;
|
||||
final int? maxLines;
|
||||
final String? Function(String?)? validator;
|
||||
|
||||
const CustomTextField({
|
||||
super.key,
|
||||
@ -28,6 +30,8 @@ class CustomTextField extends StatelessWidget {
|
||||
this.prefixIcon,
|
||||
this.suffixIcon,
|
||||
this.readOnly = false,
|
||||
this.maxLines,
|
||||
this.validator,
|
||||
});
|
||||
|
||||
@override
|
||||
@ -53,17 +57,11 @@ class CustomTextField extends StatelessWidget {
|
||||
textInputAction: textInputAction,
|
||||
textCapitalization: textCapitalization ?? TextCapitalization.none,
|
||||
readOnly: readOnly,
|
||||
maxLines: maxLines,
|
||||
validator: validator,
|
||||
decoration: InputDecoration(
|
||||
prefixIcon: prefixIcon,
|
||||
suffixIcon: suffixIcon,
|
||||
border: OutlineInputBorder(
|
||||
borderRadius: BorderRadius.circular(16.0),
|
||||
borderSide: const BorderSide(color: Colors.grey),
|
||||
),
|
||||
enabledBorder: OutlineInputBorder(
|
||||
borderRadius: BorderRadius.circular(16.0),
|
||||
borderSide: const BorderSide(color: Colors.grey),
|
||||
),
|
||||
hintText: label,
|
||||
),
|
||||
),
|
||||
|
||||
@ -22,6 +22,9 @@ ThemeData getApplicationTheme = ThemeData(
|
||||
useMaterial3: true,
|
||||
inputDecorationTheme: InputDecorationTheme(
|
||||
contentPadding: const EdgeInsets.symmetric(horizontal: 16.0),
|
||||
hintStyle: const TextStyle(
|
||||
color: AppColors.grey,
|
||||
),
|
||||
border: OutlineInputBorder(
|
||||
borderRadius: BorderRadius.circular(8.0),
|
||||
borderSide: BorderSide(color: AppColors.primary),
|
||||
|
||||
@ -45,4 +45,57 @@ class CustomerRemoteDataSource {
|
||||
return const Left('Unexpected error occurred');
|
||||
}
|
||||
}
|
||||
|
||||
Future<Either<String, bool>> createCustomer({
|
||||
required String name,
|
||||
required String phone,
|
||||
required String address,
|
||||
required String email,
|
||||
required bool isActive,
|
||||
}) async {
|
||||
try {
|
||||
final authData = await AuthLocalDataSource().getAuthData();
|
||||
final url = '${Variables.baseUrl}/api/v1/customers';
|
||||
|
||||
Map<String, dynamic> data = {
|
||||
'name': name,
|
||||
'is_active': isActive,
|
||||
};
|
||||
|
||||
if (phone.isNotEmpty) {
|
||||
data['phone'] = phone;
|
||||
}
|
||||
|
||||
if (address.isNotEmpty) {
|
||||
data['address'] = address;
|
||||
}
|
||||
|
||||
if (email.isNotEmpty) {
|
||||
data['email'] = email;
|
||||
}
|
||||
|
||||
final response = await dio.post(
|
||||
url,
|
||||
data: data,
|
||||
options: Options(
|
||||
headers: {
|
||||
'Authorization': 'Bearer ${authData.token}',
|
||||
'Accept': 'application/json',
|
||||
},
|
||||
),
|
||||
);
|
||||
|
||||
if (response.statusCode == 200 || response.statusCode == 201) {
|
||||
return const Right(true);
|
||||
} else {
|
||||
return const Left('Failed to create customer ');
|
||||
}
|
||||
} on DioException catch (e) {
|
||||
log("Dio error: ${e.message}");
|
||||
return Left(e.response?.data['message'] ?? 'Gagal membuat pelanggan');
|
||||
} catch (e) {
|
||||
log("Unexpected error: $e");
|
||||
return const Left('Unexpected error occurred');
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -2,6 +2,7 @@ import 'dart:developer';
|
||||
import 'package:enaklo_pos/core/constants/theme.dart';
|
||||
import 'package:enaklo_pos/data/datasources/customer_remote_datasource.dart';
|
||||
import 'package:enaklo_pos/data/datasources/outlet_remote_data_source.dart';
|
||||
import 'package:enaklo_pos/presentation/customer/bloc/customer_form/customer_form_bloc.dart';
|
||||
import 'package:enaklo_pos/presentation/customer/bloc/customer_loader/customer_loader_bloc.dart';
|
||||
import 'package:enaklo_pos/presentation/home/bloc/order_form/order_form_bloc.dart';
|
||||
import 'package:enaklo_pos/presentation/home/bloc/outlet_loader/outlet_loader_bloc.dart';
|
||||
@ -239,6 +240,9 @@ class _MyAppState extends State<MyApp> {
|
||||
BlocProvider(
|
||||
create: (context) => CustomerLoaderBloc(CustomerRemoteDataSource()),
|
||||
),
|
||||
BlocProvider(
|
||||
create: (context) => CustomerFormBloc(CustomerRemoteDataSource()),
|
||||
),
|
||||
],
|
||||
child: MaterialApp(
|
||||
debugShowCheckedModeBanner: false,
|
||||
|
||||
@ -0,0 +1,28 @@
|
||||
import 'package:bloc/bloc.dart';
|
||||
import 'package:enaklo_pos/data/datasources/customer_remote_datasource.dart';
|
||||
import 'package:freezed_annotation/freezed_annotation.dart';
|
||||
|
||||
part 'customer_form_event.dart';
|
||||
part 'customer_form_state.dart';
|
||||
part 'customer_form_bloc.freezed.dart';
|
||||
|
||||
class CustomerFormBloc extends Bloc<CustomerFormEvent, CustomerFormState> {
|
||||
final CustomerRemoteDataSource _customerRemoteDataSource;
|
||||
CustomerFormBloc(this._customerRemoteDataSource)
|
||||
: super(CustomerFormState.initial()) {
|
||||
on<_Create>((event, emit) async {
|
||||
emit(const _Loading());
|
||||
final result = await _customerRemoteDataSource.createCustomer(
|
||||
name: event.name,
|
||||
address: event.address,
|
||||
phone: event.phoneNumber,
|
||||
email: event.email,
|
||||
isActive: event.isActive,
|
||||
);
|
||||
result.fold(
|
||||
(l) => emit(_Error(l)),
|
||||
(r) => emit(_Success()),
|
||||
);
|
||||
});
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,908 @@
|
||||
// coverage:ignore-file
|
||||
// GENERATED CODE - DO NOT MODIFY BY HAND
|
||||
// ignore_for_file: type=lint
|
||||
// ignore_for_file: unused_element, deprecated_member_use, deprecated_member_use_from_same_package, use_function_type_syntax_for_parameters, unnecessary_const, avoid_init_to_null, invalid_override_different_default_values_named, prefer_expression_function_bodies, annotate_overrides, invalid_annotation_target, unnecessary_question_mark
|
||||
|
||||
part of 'customer_form_bloc.dart';
|
||||
|
||||
// **************************************************************************
|
||||
// FreezedGenerator
|
||||
// **************************************************************************
|
||||
|
||||
T _$identity<T>(T value) => value;
|
||||
|
||||
final _privateConstructorUsedError = UnsupportedError(
|
||||
'It seems like you constructed your class using `MyClass._()`. This constructor is only meant to be used by freezed and you are not supposed to need it nor use it.\nPlease check the documentation here for more information: https://github.com/rrousselGit/freezed#adding-getters-and-methods-to-our-models');
|
||||
|
||||
/// @nodoc
|
||||
mixin _$CustomerFormEvent {
|
||||
String get name => throw _privateConstructorUsedError;
|
||||
String get address => throw _privateConstructorUsedError;
|
||||
String get phoneNumber => throw _privateConstructorUsedError;
|
||||
String get email => throw _privateConstructorUsedError;
|
||||
bool get isActive => throw _privateConstructorUsedError;
|
||||
@optionalTypeArgs
|
||||
TResult when<TResult extends Object?>({
|
||||
required TResult Function(String name, String address, String phoneNumber,
|
||||
String email, bool isActive)
|
||||
create,
|
||||
}) =>
|
||||
throw _privateConstructorUsedError;
|
||||
@optionalTypeArgs
|
||||
TResult? whenOrNull<TResult extends Object?>({
|
||||
TResult? Function(String name, String address, String phoneNumber,
|
||||
String email, bool isActive)?
|
||||
create,
|
||||
}) =>
|
||||
throw _privateConstructorUsedError;
|
||||
@optionalTypeArgs
|
||||
TResult maybeWhen<TResult extends Object?>({
|
||||
TResult Function(String name, String address, String phoneNumber,
|
||||
String email, bool isActive)?
|
||||
create,
|
||||
required TResult orElse(),
|
||||
}) =>
|
||||
throw _privateConstructorUsedError;
|
||||
@optionalTypeArgs
|
||||
TResult map<TResult extends Object?>({
|
||||
required TResult Function(_Create value) create,
|
||||
}) =>
|
||||
throw _privateConstructorUsedError;
|
||||
@optionalTypeArgs
|
||||
TResult? mapOrNull<TResult extends Object?>({
|
||||
TResult? Function(_Create value)? create,
|
||||
}) =>
|
||||
throw _privateConstructorUsedError;
|
||||
@optionalTypeArgs
|
||||
TResult maybeMap<TResult extends Object?>({
|
||||
TResult Function(_Create value)? create,
|
||||
required TResult orElse(),
|
||||
}) =>
|
||||
throw _privateConstructorUsedError;
|
||||
|
||||
/// Create a copy of CustomerFormEvent
|
||||
/// with the given fields replaced by the non-null parameter values.
|
||||
@JsonKey(includeFromJson: false, includeToJson: false)
|
||||
$CustomerFormEventCopyWith<CustomerFormEvent> get copyWith =>
|
||||
throw _privateConstructorUsedError;
|
||||
}
|
||||
|
||||
/// @nodoc
|
||||
abstract class $CustomerFormEventCopyWith<$Res> {
|
||||
factory $CustomerFormEventCopyWith(
|
||||
CustomerFormEvent value, $Res Function(CustomerFormEvent) then) =
|
||||
_$CustomerFormEventCopyWithImpl<$Res, CustomerFormEvent>;
|
||||
@useResult
|
||||
$Res call(
|
||||
{String name,
|
||||
String address,
|
||||
String phoneNumber,
|
||||
String email,
|
||||
bool isActive});
|
||||
}
|
||||
|
||||
/// @nodoc
|
||||
class _$CustomerFormEventCopyWithImpl<$Res, $Val extends CustomerFormEvent>
|
||||
implements $CustomerFormEventCopyWith<$Res> {
|
||||
_$CustomerFormEventCopyWithImpl(this._value, this._then);
|
||||
|
||||
// ignore: unused_field
|
||||
final $Val _value;
|
||||
// ignore: unused_field
|
||||
final $Res Function($Val) _then;
|
||||
|
||||
/// Create a copy of CustomerFormEvent
|
||||
/// with the given fields replaced by the non-null parameter values.
|
||||
@pragma('vm:prefer-inline')
|
||||
@override
|
||||
$Res call({
|
||||
Object? name = null,
|
||||
Object? address = null,
|
||||
Object? phoneNumber = null,
|
||||
Object? email = null,
|
||||
Object? isActive = null,
|
||||
}) {
|
||||
return _then(_value.copyWith(
|
||||
name: null == name
|
||||
? _value.name
|
||||
: name // ignore: cast_nullable_to_non_nullable
|
||||
as String,
|
||||
address: null == address
|
||||
? _value.address
|
||||
: address // ignore: cast_nullable_to_non_nullable
|
||||
as String,
|
||||
phoneNumber: null == phoneNumber
|
||||
? _value.phoneNumber
|
||||
: phoneNumber // ignore: cast_nullable_to_non_nullable
|
||||
as String,
|
||||
email: null == email
|
||||
? _value.email
|
||||
: email // ignore: cast_nullable_to_non_nullable
|
||||
as String,
|
||||
isActive: null == isActive
|
||||
? _value.isActive
|
||||
: isActive // ignore: cast_nullable_to_non_nullable
|
||||
as bool,
|
||||
) as $Val);
|
||||
}
|
||||
}
|
||||
|
||||
/// @nodoc
|
||||
abstract class _$$CreateImplCopyWith<$Res>
|
||||
implements $CustomerFormEventCopyWith<$Res> {
|
||||
factory _$$CreateImplCopyWith(
|
||||
_$CreateImpl value, $Res Function(_$CreateImpl) then) =
|
||||
__$$CreateImplCopyWithImpl<$Res>;
|
||||
@override
|
||||
@useResult
|
||||
$Res call(
|
||||
{String name,
|
||||
String address,
|
||||
String phoneNumber,
|
||||
String email,
|
||||
bool isActive});
|
||||
}
|
||||
|
||||
/// @nodoc
|
||||
class __$$CreateImplCopyWithImpl<$Res>
|
||||
extends _$CustomerFormEventCopyWithImpl<$Res, _$CreateImpl>
|
||||
implements _$$CreateImplCopyWith<$Res> {
|
||||
__$$CreateImplCopyWithImpl(
|
||||
_$CreateImpl _value, $Res Function(_$CreateImpl) _then)
|
||||
: super(_value, _then);
|
||||
|
||||
/// Create a copy of CustomerFormEvent
|
||||
/// with the given fields replaced by the non-null parameter values.
|
||||
@pragma('vm:prefer-inline')
|
||||
@override
|
||||
$Res call({
|
||||
Object? name = null,
|
||||
Object? address = null,
|
||||
Object? phoneNumber = null,
|
||||
Object? email = null,
|
||||
Object? isActive = null,
|
||||
}) {
|
||||
return _then(_$CreateImpl(
|
||||
name: null == name
|
||||
? _value.name
|
||||
: name // ignore: cast_nullable_to_non_nullable
|
||||
as String,
|
||||
address: null == address
|
||||
? _value.address
|
||||
: address // ignore: cast_nullable_to_non_nullable
|
||||
as String,
|
||||
phoneNumber: null == phoneNumber
|
||||
? _value.phoneNumber
|
||||
: phoneNumber // ignore: cast_nullable_to_non_nullable
|
||||
as String,
|
||||
email: null == email
|
||||
? _value.email
|
||||
: email // ignore: cast_nullable_to_non_nullable
|
||||
as String,
|
||||
isActive: null == isActive
|
||||
? _value.isActive
|
||||
: isActive // ignore: cast_nullable_to_non_nullable
|
||||
as bool,
|
||||
));
|
||||
}
|
||||
}
|
||||
|
||||
/// @nodoc
|
||||
|
||||
class _$CreateImpl implements _Create {
|
||||
const _$CreateImpl(
|
||||
{required this.name,
|
||||
required this.address,
|
||||
required this.phoneNumber,
|
||||
required this.email,
|
||||
required this.isActive});
|
||||
|
||||
@override
|
||||
final String name;
|
||||
@override
|
||||
final String address;
|
||||
@override
|
||||
final String phoneNumber;
|
||||
@override
|
||||
final String email;
|
||||
@override
|
||||
final bool isActive;
|
||||
|
||||
@override
|
||||
String toString() {
|
||||
return 'CustomerFormEvent.create(name: $name, address: $address, phoneNumber: $phoneNumber, email: $email, isActive: $isActive)';
|
||||
}
|
||||
|
||||
@override
|
||||
bool operator ==(Object other) {
|
||||
return identical(this, other) ||
|
||||
(other.runtimeType == runtimeType &&
|
||||
other is _$CreateImpl &&
|
||||
(identical(other.name, name) || other.name == name) &&
|
||||
(identical(other.address, address) || other.address == address) &&
|
||||
(identical(other.phoneNumber, phoneNumber) ||
|
||||
other.phoneNumber == phoneNumber) &&
|
||||
(identical(other.email, email) || other.email == email) &&
|
||||
(identical(other.isActive, isActive) ||
|
||||
other.isActive == isActive));
|
||||
}
|
||||
|
||||
@override
|
||||
int get hashCode =>
|
||||
Object.hash(runtimeType, name, address, phoneNumber, email, isActive);
|
||||
|
||||
/// Create a copy of CustomerFormEvent
|
||||
/// with the given fields replaced by the non-null parameter values.
|
||||
@JsonKey(includeFromJson: false, includeToJson: false)
|
||||
@override
|
||||
@pragma('vm:prefer-inline')
|
||||
_$$CreateImplCopyWith<_$CreateImpl> get copyWith =>
|
||||
__$$CreateImplCopyWithImpl<_$CreateImpl>(this, _$identity);
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult when<TResult extends Object?>({
|
||||
required TResult Function(String name, String address, String phoneNumber,
|
||||
String email, bool isActive)
|
||||
create,
|
||||
}) {
|
||||
return create(name, address, phoneNumber, email, isActive);
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult? whenOrNull<TResult extends Object?>({
|
||||
TResult? Function(String name, String address, String phoneNumber,
|
||||
String email, bool isActive)?
|
||||
create,
|
||||
}) {
|
||||
return create?.call(name, address, phoneNumber, email, isActive);
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult maybeWhen<TResult extends Object?>({
|
||||
TResult Function(String name, String address, String phoneNumber,
|
||||
String email, bool isActive)?
|
||||
create,
|
||||
required TResult orElse(),
|
||||
}) {
|
||||
if (create != null) {
|
||||
return create(name, address, phoneNumber, email, isActive);
|
||||
}
|
||||
return orElse();
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult map<TResult extends Object?>({
|
||||
required TResult Function(_Create value) create,
|
||||
}) {
|
||||
return create(this);
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult? mapOrNull<TResult extends Object?>({
|
||||
TResult? Function(_Create value)? create,
|
||||
}) {
|
||||
return create?.call(this);
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult maybeMap<TResult extends Object?>({
|
||||
TResult Function(_Create value)? create,
|
||||
required TResult orElse(),
|
||||
}) {
|
||||
if (create != null) {
|
||||
return create(this);
|
||||
}
|
||||
return orElse();
|
||||
}
|
||||
}
|
||||
|
||||
abstract class _Create implements CustomerFormEvent {
|
||||
const factory _Create(
|
||||
{required final String name,
|
||||
required final String address,
|
||||
required final String phoneNumber,
|
||||
required final String email,
|
||||
required final bool isActive}) = _$CreateImpl;
|
||||
|
||||
@override
|
||||
String get name;
|
||||
@override
|
||||
String get address;
|
||||
@override
|
||||
String get phoneNumber;
|
||||
@override
|
||||
String get email;
|
||||
@override
|
||||
bool get isActive;
|
||||
|
||||
/// Create a copy of CustomerFormEvent
|
||||
/// with the given fields replaced by the non-null parameter values.
|
||||
@override
|
||||
@JsonKey(includeFromJson: false, includeToJson: false)
|
||||
_$$CreateImplCopyWith<_$CreateImpl> get copyWith =>
|
||||
throw _privateConstructorUsedError;
|
||||
}
|
||||
|
||||
/// @nodoc
|
||||
mixin _$CustomerFormState {
|
||||
@optionalTypeArgs
|
||||
TResult when<TResult extends Object?>({
|
||||
required TResult Function() initial,
|
||||
required TResult Function() loading,
|
||||
required TResult Function() success,
|
||||
required TResult Function(String message) error,
|
||||
}) =>
|
||||
throw _privateConstructorUsedError;
|
||||
@optionalTypeArgs
|
||||
TResult? whenOrNull<TResult extends Object?>({
|
||||
TResult? Function()? initial,
|
||||
TResult? Function()? loading,
|
||||
TResult? Function()? success,
|
||||
TResult? Function(String message)? error,
|
||||
}) =>
|
||||
throw _privateConstructorUsedError;
|
||||
@optionalTypeArgs
|
||||
TResult maybeWhen<TResult extends Object?>({
|
||||
TResult Function()? initial,
|
||||
TResult Function()? loading,
|
||||
TResult Function()? success,
|
||||
TResult Function(String message)? error,
|
||||
required TResult orElse(),
|
||||
}) =>
|
||||
throw _privateConstructorUsedError;
|
||||
@optionalTypeArgs
|
||||
TResult map<TResult extends Object?>({
|
||||
required TResult Function(_Initial value) initial,
|
||||
required TResult Function(_Loading value) loading,
|
||||
required TResult Function(_Success value) success,
|
||||
required TResult Function(_Error value) error,
|
||||
}) =>
|
||||
throw _privateConstructorUsedError;
|
||||
@optionalTypeArgs
|
||||
TResult? mapOrNull<TResult extends Object?>({
|
||||
TResult? Function(_Initial value)? initial,
|
||||
TResult? Function(_Loading value)? loading,
|
||||
TResult? Function(_Success value)? success,
|
||||
TResult? Function(_Error value)? error,
|
||||
}) =>
|
||||
throw _privateConstructorUsedError;
|
||||
@optionalTypeArgs
|
||||
TResult maybeMap<TResult extends Object?>({
|
||||
TResult Function(_Initial value)? initial,
|
||||
TResult Function(_Loading value)? loading,
|
||||
TResult Function(_Success value)? success,
|
||||
TResult Function(_Error value)? error,
|
||||
required TResult orElse(),
|
||||
}) =>
|
||||
throw _privateConstructorUsedError;
|
||||
}
|
||||
|
||||
/// @nodoc
|
||||
abstract class $CustomerFormStateCopyWith<$Res> {
|
||||
factory $CustomerFormStateCopyWith(
|
||||
CustomerFormState value, $Res Function(CustomerFormState) then) =
|
||||
_$CustomerFormStateCopyWithImpl<$Res, CustomerFormState>;
|
||||
}
|
||||
|
||||
/// @nodoc
|
||||
class _$CustomerFormStateCopyWithImpl<$Res, $Val extends CustomerFormState>
|
||||
implements $CustomerFormStateCopyWith<$Res> {
|
||||
_$CustomerFormStateCopyWithImpl(this._value, this._then);
|
||||
|
||||
// ignore: unused_field
|
||||
final $Val _value;
|
||||
// ignore: unused_field
|
||||
final $Res Function($Val) _then;
|
||||
|
||||
/// Create a copy of CustomerFormState
|
||||
/// with the given fields replaced by the non-null parameter values.
|
||||
}
|
||||
|
||||
/// @nodoc
|
||||
abstract class _$$InitialImplCopyWith<$Res> {
|
||||
factory _$$InitialImplCopyWith(
|
||||
_$InitialImpl value, $Res Function(_$InitialImpl) then) =
|
||||
__$$InitialImplCopyWithImpl<$Res>;
|
||||
}
|
||||
|
||||
/// @nodoc
|
||||
class __$$InitialImplCopyWithImpl<$Res>
|
||||
extends _$CustomerFormStateCopyWithImpl<$Res, _$InitialImpl>
|
||||
implements _$$InitialImplCopyWith<$Res> {
|
||||
__$$InitialImplCopyWithImpl(
|
||||
_$InitialImpl _value, $Res Function(_$InitialImpl) _then)
|
||||
: super(_value, _then);
|
||||
|
||||
/// Create a copy of CustomerFormState
|
||||
/// with the given fields replaced by the non-null parameter values.
|
||||
}
|
||||
|
||||
/// @nodoc
|
||||
|
||||
class _$InitialImpl implements _Initial {
|
||||
const _$InitialImpl();
|
||||
|
||||
@override
|
||||
String toString() {
|
||||
return 'CustomerFormState.initial()';
|
||||
}
|
||||
|
||||
@override
|
||||
bool operator ==(Object other) {
|
||||
return identical(this, other) ||
|
||||
(other.runtimeType == runtimeType && other is _$InitialImpl);
|
||||
}
|
||||
|
||||
@override
|
||||
int get hashCode => runtimeType.hashCode;
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult when<TResult extends Object?>({
|
||||
required TResult Function() initial,
|
||||
required TResult Function() loading,
|
||||
required TResult Function() success,
|
||||
required TResult Function(String message) error,
|
||||
}) {
|
||||
return initial();
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult? whenOrNull<TResult extends Object?>({
|
||||
TResult? Function()? initial,
|
||||
TResult? Function()? loading,
|
||||
TResult? Function()? success,
|
||||
TResult? Function(String message)? error,
|
||||
}) {
|
||||
return initial?.call();
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult maybeWhen<TResult extends Object?>({
|
||||
TResult Function()? initial,
|
||||
TResult Function()? loading,
|
||||
TResult Function()? success,
|
||||
TResult Function(String message)? error,
|
||||
required TResult orElse(),
|
||||
}) {
|
||||
if (initial != null) {
|
||||
return initial();
|
||||
}
|
||||
return orElse();
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult map<TResult extends Object?>({
|
||||
required TResult Function(_Initial value) initial,
|
||||
required TResult Function(_Loading value) loading,
|
||||
required TResult Function(_Success value) success,
|
||||
required TResult Function(_Error value) error,
|
||||
}) {
|
||||
return initial(this);
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult? mapOrNull<TResult extends Object?>({
|
||||
TResult? Function(_Initial value)? initial,
|
||||
TResult? Function(_Loading value)? loading,
|
||||
TResult? Function(_Success value)? success,
|
||||
TResult? Function(_Error value)? error,
|
||||
}) {
|
||||
return initial?.call(this);
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult maybeMap<TResult extends Object?>({
|
||||
TResult Function(_Initial value)? initial,
|
||||
TResult Function(_Loading value)? loading,
|
||||
TResult Function(_Success value)? success,
|
||||
TResult Function(_Error value)? error,
|
||||
required TResult orElse(),
|
||||
}) {
|
||||
if (initial != null) {
|
||||
return initial(this);
|
||||
}
|
||||
return orElse();
|
||||
}
|
||||
}
|
||||
|
||||
abstract class _Initial implements CustomerFormState {
|
||||
const factory _Initial() = _$InitialImpl;
|
||||
}
|
||||
|
||||
/// @nodoc
|
||||
abstract class _$$LoadingImplCopyWith<$Res> {
|
||||
factory _$$LoadingImplCopyWith(
|
||||
_$LoadingImpl value, $Res Function(_$LoadingImpl) then) =
|
||||
__$$LoadingImplCopyWithImpl<$Res>;
|
||||
}
|
||||
|
||||
/// @nodoc
|
||||
class __$$LoadingImplCopyWithImpl<$Res>
|
||||
extends _$CustomerFormStateCopyWithImpl<$Res, _$LoadingImpl>
|
||||
implements _$$LoadingImplCopyWith<$Res> {
|
||||
__$$LoadingImplCopyWithImpl(
|
||||
_$LoadingImpl _value, $Res Function(_$LoadingImpl) _then)
|
||||
: super(_value, _then);
|
||||
|
||||
/// Create a copy of CustomerFormState
|
||||
/// with the given fields replaced by the non-null parameter values.
|
||||
}
|
||||
|
||||
/// @nodoc
|
||||
|
||||
class _$LoadingImpl implements _Loading {
|
||||
const _$LoadingImpl();
|
||||
|
||||
@override
|
||||
String toString() {
|
||||
return 'CustomerFormState.loading()';
|
||||
}
|
||||
|
||||
@override
|
||||
bool operator ==(Object other) {
|
||||
return identical(this, other) ||
|
||||
(other.runtimeType == runtimeType && other is _$LoadingImpl);
|
||||
}
|
||||
|
||||
@override
|
||||
int get hashCode => runtimeType.hashCode;
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult when<TResult extends Object?>({
|
||||
required TResult Function() initial,
|
||||
required TResult Function() loading,
|
||||
required TResult Function() success,
|
||||
required TResult Function(String message) error,
|
||||
}) {
|
||||
return loading();
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult? whenOrNull<TResult extends Object?>({
|
||||
TResult? Function()? initial,
|
||||
TResult? Function()? loading,
|
||||
TResult? Function()? success,
|
||||
TResult? Function(String message)? error,
|
||||
}) {
|
||||
return loading?.call();
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult maybeWhen<TResult extends Object?>({
|
||||
TResult Function()? initial,
|
||||
TResult Function()? loading,
|
||||
TResult Function()? success,
|
||||
TResult Function(String message)? error,
|
||||
required TResult orElse(),
|
||||
}) {
|
||||
if (loading != null) {
|
||||
return loading();
|
||||
}
|
||||
return orElse();
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult map<TResult extends Object?>({
|
||||
required TResult Function(_Initial value) initial,
|
||||
required TResult Function(_Loading value) loading,
|
||||
required TResult Function(_Success value) success,
|
||||
required TResult Function(_Error value) error,
|
||||
}) {
|
||||
return loading(this);
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult? mapOrNull<TResult extends Object?>({
|
||||
TResult? Function(_Initial value)? initial,
|
||||
TResult? Function(_Loading value)? loading,
|
||||
TResult? Function(_Success value)? success,
|
||||
TResult? Function(_Error value)? error,
|
||||
}) {
|
||||
return loading?.call(this);
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult maybeMap<TResult extends Object?>({
|
||||
TResult Function(_Initial value)? initial,
|
||||
TResult Function(_Loading value)? loading,
|
||||
TResult Function(_Success value)? success,
|
||||
TResult Function(_Error value)? error,
|
||||
required TResult orElse(),
|
||||
}) {
|
||||
if (loading != null) {
|
||||
return loading(this);
|
||||
}
|
||||
return orElse();
|
||||
}
|
||||
}
|
||||
|
||||
abstract class _Loading implements CustomerFormState {
|
||||
const factory _Loading() = _$LoadingImpl;
|
||||
}
|
||||
|
||||
/// @nodoc
|
||||
abstract class _$$SuccessImplCopyWith<$Res> {
|
||||
factory _$$SuccessImplCopyWith(
|
||||
_$SuccessImpl value, $Res Function(_$SuccessImpl) then) =
|
||||
__$$SuccessImplCopyWithImpl<$Res>;
|
||||
}
|
||||
|
||||
/// @nodoc
|
||||
class __$$SuccessImplCopyWithImpl<$Res>
|
||||
extends _$CustomerFormStateCopyWithImpl<$Res, _$SuccessImpl>
|
||||
implements _$$SuccessImplCopyWith<$Res> {
|
||||
__$$SuccessImplCopyWithImpl(
|
||||
_$SuccessImpl _value, $Res Function(_$SuccessImpl) _then)
|
||||
: super(_value, _then);
|
||||
|
||||
/// Create a copy of CustomerFormState
|
||||
/// with the given fields replaced by the non-null parameter values.
|
||||
}
|
||||
|
||||
/// @nodoc
|
||||
|
||||
class _$SuccessImpl implements _Success {
|
||||
const _$SuccessImpl();
|
||||
|
||||
@override
|
||||
String toString() {
|
||||
return 'CustomerFormState.success()';
|
||||
}
|
||||
|
||||
@override
|
||||
bool operator ==(Object other) {
|
||||
return identical(this, other) ||
|
||||
(other.runtimeType == runtimeType && other is _$SuccessImpl);
|
||||
}
|
||||
|
||||
@override
|
||||
int get hashCode => runtimeType.hashCode;
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult when<TResult extends Object?>({
|
||||
required TResult Function() initial,
|
||||
required TResult Function() loading,
|
||||
required TResult Function() success,
|
||||
required TResult Function(String message) error,
|
||||
}) {
|
||||
return success();
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult? whenOrNull<TResult extends Object?>({
|
||||
TResult? Function()? initial,
|
||||
TResult? Function()? loading,
|
||||
TResult? Function()? success,
|
||||
TResult? Function(String message)? error,
|
||||
}) {
|
||||
return success?.call();
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult maybeWhen<TResult extends Object?>({
|
||||
TResult Function()? initial,
|
||||
TResult Function()? loading,
|
||||
TResult Function()? success,
|
||||
TResult Function(String message)? error,
|
||||
required TResult orElse(),
|
||||
}) {
|
||||
if (success != null) {
|
||||
return success();
|
||||
}
|
||||
return orElse();
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult map<TResult extends Object?>({
|
||||
required TResult Function(_Initial value) initial,
|
||||
required TResult Function(_Loading value) loading,
|
||||
required TResult Function(_Success value) success,
|
||||
required TResult Function(_Error value) error,
|
||||
}) {
|
||||
return success(this);
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult? mapOrNull<TResult extends Object?>({
|
||||
TResult? Function(_Initial value)? initial,
|
||||
TResult? Function(_Loading value)? loading,
|
||||
TResult? Function(_Success value)? success,
|
||||
TResult? Function(_Error value)? error,
|
||||
}) {
|
||||
return success?.call(this);
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult maybeMap<TResult extends Object?>({
|
||||
TResult Function(_Initial value)? initial,
|
||||
TResult Function(_Loading value)? loading,
|
||||
TResult Function(_Success value)? success,
|
||||
TResult Function(_Error value)? error,
|
||||
required TResult orElse(),
|
||||
}) {
|
||||
if (success != null) {
|
||||
return success(this);
|
||||
}
|
||||
return orElse();
|
||||
}
|
||||
}
|
||||
|
||||
abstract class _Success implements CustomerFormState {
|
||||
const factory _Success() = _$SuccessImpl;
|
||||
}
|
||||
|
||||
/// @nodoc
|
||||
abstract class _$$ErrorImplCopyWith<$Res> {
|
||||
factory _$$ErrorImplCopyWith(
|
||||
_$ErrorImpl value, $Res Function(_$ErrorImpl) then) =
|
||||
__$$ErrorImplCopyWithImpl<$Res>;
|
||||
@useResult
|
||||
$Res call({String message});
|
||||
}
|
||||
|
||||
/// @nodoc
|
||||
class __$$ErrorImplCopyWithImpl<$Res>
|
||||
extends _$CustomerFormStateCopyWithImpl<$Res, _$ErrorImpl>
|
||||
implements _$$ErrorImplCopyWith<$Res> {
|
||||
__$$ErrorImplCopyWithImpl(
|
||||
_$ErrorImpl _value, $Res Function(_$ErrorImpl) _then)
|
||||
: super(_value, _then);
|
||||
|
||||
/// Create a copy of CustomerFormState
|
||||
/// with the given fields replaced by the non-null parameter values.
|
||||
@pragma('vm:prefer-inline')
|
||||
@override
|
||||
$Res call({
|
||||
Object? message = null,
|
||||
}) {
|
||||
return _then(_$ErrorImpl(
|
||||
null == message
|
||||
? _value.message
|
||||
: message // ignore: cast_nullable_to_non_nullable
|
||||
as String,
|
||||
));
|
||||
}
|
||||
}
|
||||
|
||||
/// @nodoc
|
||||
|
||||
class _$ErrorImpl implements _Error {
|
||||
const _$ErrorImpl(this.message);
|
||||
|
||||
@override
|
||||
final String message;
|
||||
|
||||
@override
|
||||
String toString() {
|
||||
return 'CustomerFormState.error(message: $message)';
|
||||
}
|
||||
|
||||
@override
|
||||
bool operator ==(Object other) {
|
||||
return identical(this, other) ||
|
||||
(other.runtimeType == runtimeType &&
|
||||
other is _$ErrorImpl &&
|
||||
(identical(other.message, message) || other.message == message));
|
||||
}
|
||||
|
||||
@override
|
||||
int get hashCode => Object.hash(runtimeType, message);
|
||||
|
||||
/// Create a copy of CustomerFormState
|
||||
/// with the given fields replaced by the non-null parameter values.
|
||||
@JsonKey(includeFromJson: false, includeToJson: false)
|
||||
@override
|
||||
@pragma('vm:prefer-inline')
|
||||
_$$ErrorImplCopyWith<_$ErrorImpl> get copyWith =>
|
||||
__$$ErrorImplCopyWithImpl<_$ErrorImpl>(this, _$identity);
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult when<TResult extends Object?>({
|
||||
required TResult Function() initial,
|
||||
required TResult Function() loading,
|
||||
required TResult Function() success,
|
||||
required TResult Function(String message) error,
|
||||
}) {
|
||||
return error(message);
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult? whenOrNull<TResult extends Object?>({
|
||||
TResult? Function()? initial,
|
||||
TResult? Function()? loading,
|
||||
TResult? Function()? success,
|
||||
TResult? Function(String message)? error,
|
||||
}) {
|
||||
return error?.call(message);
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult maybeWhen<TResult extends Object?>({
|
||||
TResult Function()? initial,
|
||||
TResult Function()? loading,
|
||||
TResult Function()? success,
|
||||
TResult Function(String message)? error,
|
||||
required TResult orElse(),
|
||||
}) {
|
||||
if (error != null) {
|
||||
return error(message);
|
||||
}
|
||||
return orElse();
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult map<TResult extends Object?>({
|
||||
required TResult Function(_Initial value) initial,
|
||||
required TResult Function(_Loading value) loading,
|
||||
required TResult Function(_Success value) success,
|
||||
required TResult Function(_Error value) error,
|
||||
}) {
|
||||
return error(this);
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult? mapOrNull<TResult extends Object?>({
|
||||
TResult? Function(_Initial value)? initial,
|
||||
TResult? Function(_Loading value)? loading,
|
||||
TResult? Function(_Success value)? success,
|
||||
TResult? Function(_Error value)? error,
|
||||
}) {
|
||||
return error?.call(this);
|
||||
}
|
||||
|
||||
@override
|
||||
@optionalTypeArgs
|
||||
TResult maybeMap<TResult extends Object?>({
|
||||
TResult Function(_Initial value)? initial,
|
||||
TResult Function(_Loading value)? loading,
|
||||
TResult Function(_Success value)? success,
|
||||
TResult Function(_Error value)? error,
|
||||
required TResult orElse(),
|
||||
}) {
|
||||
if (error != null) {
|
||||
return error(this);
|
||||
}
|
||||
return orElse();
|
||||
}
|
||||
}
|
||||
|
||||
abstract class _Error implements CustomerFormState {
|
||||
const factory _Error(final String message) = _$ErrorImpl;
|
||||
|
||||
String get message;
|
||||
|
||||
/// Create a copy of CustomerFormState
|
||||
/// with the given fields replaced by the non-null parameter values.
|
||||
@JsonKey(includeFromJson: false, includeToJson: false)
|
||||
_$$ErrorImplCopyWith<_$ErrorImpl> get copyWith =>
|
||||
throw _privateConstructorUsedError;
|
||||
}
|
||||
@ -0,0 +1,11 @@
|
||||
part of 'customer_form_bloc.dart';
|
||||
|
||||
@freezed
|
||||
class CustomerFormEvent with _$CustomerFormEvent {
|
||||
const factory CustomerFormEvent.create(
|
||||
{required String name,
|
||||
required String address,
|
||||
required String phoneNumber,
|
||||
required String email,
|
||||
required bool isActive}) = _Create;
|
||||
}
|
||||
@ -0,0 +1,9 @@
|
||||
part of 'customer_form_bloc.dart';
|
||||
|
||||
@freezed
|
||||
class CustomerFormState with _$CustomerFormState {
|
||||
const factory CustomerFormState.initial() = _Initial;
|
||||
const factory CustomerFormState.loading() = _Loading;
|
||||
const factory CustomerFormState.success() = _Success;
|
||||
const factory CustomerFormState.error(String message) = _Error;
|
||||
}
|
||||
121
lib/presentation/customer/dialog/form_customer_dialog.dart
Normal file
121
lib/presentation/customer/dialog/form_customer_dialog.dart
Normal file
@ -0,0 +1,121 @@
|
||||
import 'package:enaklo_pos/core/components/components.dart';
|
||||
import 'package:enaklo_pos/core/components/custom_modal_dialog.dart';
|
||||
import 'package:enaklo_pos/core/constants/colors.dart';
|
||||
import 'package:enaklo_pos/presentation/customer/bloc/customer_form/customer_form_bloc.dart';
|
||||
import 'package:enaklo_pos/presentation/customer/bloc/customer_loader/customer_loader_bloc.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_bloc/flutter_bloc.dart';
|
||||
|
||||
class FormCustomerDialog extends StatefulWidget {
|
||||
const FormCustomerDialog({super.key});
|
||||
|
||||
@override
|
||||
State<FormCustomerDialog> createState() => _FormCustomerDialogState();
|
||||
}
|
||||
|
||||
class _FormCustomerDialogState extends State<FormCustomerDialog> {
|
||||
TextEditingController nameController = TextEditingController();
|
||||
TextEditingController phoneController = TextEditingController();
|
||||
TextEditingController emailController = TextEditingController();
|
||||
TextEditingController addressController = TextEditingController();
|
||||
|
||||
final _formKey = GlobalKey<FormState>();
|
||||
|
||||
void onSave() async {
|
||||
if (_formKey.currentState!.validate()) {
|
||||
context.read<CustomerFormBloc>().add(
|
||||
CustomerFormEvent.create(
|
||||
name: nameController.text,
|
||||
phoneNumber: phoneController.text,
|
||||
email: emailController.text,
|
||||
address: addressController.text,
|
||||
isActive: true,
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return CustomModalDialog(
|
||||
title: 'Tambah Pelanggan',
|
||||
subtitle: 'Tambahkan pelanggan baru',
|
||||
contentPadding:
|
||||
const EdgeInsets.symmetric(horizontal: 16.0, vertical: 24.0),
|
||||
child: Form(
|
||||
key: _formKey,
|
||||
child: Column(
|
||||
children: [
|
||||
CustomTextField(
|
||||
controller: nameController,
|
||||
label: 'Name *',
|
||||
validator: (value) {
|
||||
if (value == null || value.isEmpty) {
|
||||
return 'Nama harus diisi';
|
||||
}
|
||||
return null;
|
||||
},
|
||||
),
|
||||
SpaceHeight(16),
|
||||
CustomTextField(
|
||||
controller: emailController,
|
||||
label: 'Email (Opsional)',
|
||||
),
|
||||
SpaceHeight(16),
|
||||
CustomTextField(
|
||||
controller: phoneController,
|
||||
keyboardType: TextInputType.phone,
|
||||
label: 'No. Handphone (Opsional)',
|
||||
),
|
||||
SpaceHeight(16),
|
||||
CustomTextField(
|
||||
controller: addressController,
|
||||
label: 'Alamat (Opsional)',
|
||||
maxLines: 5,
|
||||
),
|
||||
SpaceHeight(24),
|
||||
BlocListener<CustomerFormBloc, CustomerFormState>(
|
||||
listener: (context, state) {
|
||||
state.maybeWhen(
|
||||
orElse: () {},
|
||||
success: () {
|
||||
Navigator.pop(context);
|
||||
ScaffoldMessenger.of(context).showSnackBar(
|
||||
const SnackBar(
|
||||
content: Text('Pelanggan berhasil disimpan'),
|
||||
backgroundColor: AppColors.green,
|
||||
),
|
||||
);
|
||||
context
|
||||
.read<CustomerLoaderBloc>()
|
||||
.add(const CustomerLoaderEvent.getCustomer());
|
||||
},
|
||||
error: (message) =>
|
||||
ScaffoldMessenger.of(context).showSnackBar(
|
||||
SnackBar(
|
||||
content: Text(message),
|
||||
backgroundColor: AppColors.red,
|
||||
),
|
||||
),
|
||||
);
|
||||
},
|
||||
child: BlocBuilder<CustomerFormBloc, CustomerFormState>(
|
||||
builder: (context, state) {
|
||||
return state.maybeWhen(
|
||||
orElse: () => Button.filled(
|
||||
onPressed: onSave,
|
||||
label: 'Simpan',
|
||||
),
|
||||
loading: () => Center(
|
||||
child: const CircularProgressIndicator(),
|
||||
),
|
||||
);
|
||||
},
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
@ -1,6 +1,7 @@
|
||||
import 'package:enaklo_pos/core/components/components.dart';
|
||||
import 'package:enaklo_pos/core/constants/colors.dart';
|
||||
import 'package:enaklo_pos/core/extensions/build_context_ext.dart';
|
||||
import 'package:enaklo_pos/presentation/customer/dialog/form_customer_dialog.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
|
||||
class CustomerTitle extends StatelessWidget {
|
||||
@ -8,9 +9,7 @@ class CustomerTitle extends StatelessWidget {
|
||||
final Function(String) onChanged;
|
||||
|
||||
const CustomerTitle(
|
||||
{super.key,
|
||||
required this.onChanged,
|
||||
required this.title});
|
||||
{super.key, required this.onChanged, required this.title});
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
@ -85,7 +84,7 @@ class CustomerTitle extends StatelessWidget {
|
||||
GestureDetector(
|
||||
onTap: () => showDialog(
|
||||
context: context,
|
||||
builder: (context) => Container(),
|
||||
builder: (context) => FormCustomerDialog(),
|
||||
),
|
||||
child: Container(
|
||||
height: 40,
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user