import 'package:built_value/built_value.dart';
import 'package:built_collection/built_collection.dart';
import 'package:built_value/serializer.dart';
import 'package:invoiceninja_flutter/redux/app/app_state.dart';
import 'package:invoiceninja_flutter/data/models/models.dart';
import 'package:invoiceninja_flutter/utils/formatting.dart';
import 'package:invoiceninja_flutter/utils/strings.dart';

part 'stub_model.g.dart';

abstract class StubListResponse
    implements Built<StubListResponse, StubListResponseBuilder> {
  factory StubListResponse([void updates(StubListResponseBuilder b)]) =
      _$StubListResponse;

  StubListResponse._();

  @override
@memoized
  int get hashCode;

  BuiltList<StubEntity> get data;

  static Serializer<StubListResponse> get serializer =>
      _$stubListResponseSerializer;
}

abstract class StubItemResponse
    implements Built<StubItemResponse, StubItemResponseBuilder> {
  factory StubItemResponse([void updates(StubItemResponseBuilder b)]) =
      _$StubItemResponse;

  StubItemResponse._();

  @override
@memoized
  int get hashCode;

  StubEntity get data;

  static Serializer<StubItemResponse> get serializer =>
      _$stubItemResponseSerializer;
}

class StubFields {
  // STARTER: fields - do not remove comment
}

abstract class StubEntity extends Object with BaseEntity implements Built<StubEntity, StubEntityBuilder> {

  factory StubEntity({String id, AppState state}) {
    return _$StubEntity._(
      id: id ?? BaseEntity.nextId,
      isChanged: false,
      isDeleted: false,
      createdAt: 0,
      updatedAt: 0,
      createdUserId: '',
      assignedUserId: '',
      archivedAt: 0,
      // STARTER: constructor - do not remove comment
    );
  }

  StubEntity._();

  @override
@memoized
  int get hashCode;

  // STARTER: properties - do not remove comment

  @override
  EntityType get entityType => EntityType.stub;


  @override
  List<EntityAction> getActions(
      {UserCompanyEntity userCompany,
      ClientEntity client,
      bool includeEdit = false,
      bool multiselect = false}) {
    final actions = <EntityAction>[];

    if (!isDeleted && !multiselect && includeEdit && userCompany.canEditEntity(this)) {
      actions.add(EntityAction.edit);
    }

    if (actions.isNotEmpty && actions.last != null) {
      actions.add(null);
    }

    return actions..addAll(super.getActions(userCompany: userCompany));
  }

  int compareTo(StubEntity stub, String sortField, bool sortAscending) {
    int response = 0;
    final stubA = sortAscending ? this : stub;
    final stubB = sortAscending ? stub: this;

    switch (sortField) {
      // STARTER: sort switch - do not remove comment
            default:
              print('## ERROR: sort by stub.$sortField is not implemented');
              break;

    }

    if (response == 0) {
      // STARTER: sort default - do not remove comment
    } else {
      return response;
    }
  }

  @override
  bool matchesFilter(String filter) {
    return matchesStrings(
      haystacks: [
        //
      ],
      needle: filter,
    );
  }

  @override
  String matchesFilterValue(String filter) {
    return matchesStringsValue(
      haystacks: [
        //
      ],
      needle: filter,
    );
  }

  @override
  String get listDisplayName => null;

  @override
  double get listDisplayAmount => null;

  @override
  FormatNumberType get listDisplayAmountType => null;

  static Serializer<StubEntity> get serializer => _$stubEntitySerializer;
}
