visitFieldElement method

  1. @override
void visitFieldElement(
  1. FieldElement element
)
override

Implementation

@override
void visitFieldElement(FieldElement element) {
  if (element.isPrivate) {
    return;
  }
  final type = element.type.toString();
  final name = element.name;
  final isFinal = element.isFinal;
  final hasSetter = element.setter != null;
  final isSilent = silentAnnotation.hasAnnotationOf(element);
  final isCollection = element.type.isDartCoreList ||
      element.type.isDartCoreSet ||
      element.type.isDartCoreMap;
  final needSubscription =
      (isCollection && !isSilent) || !(isSilent || isFinal);

  if (isFinal && !isCollection) {
    // redirection
    classBuilder.methods.add(
      Method(
        (builder) => builder
          ..annotations.add(CodeExpression(Code('override')))
          ..returns = Reference(type)
          ..type = MethodType.getter
          ..name = name
          ..body = Code('''
return \$src.$name;
'''),
      ),
    );
  }
  if (isSilent && !isFinal) {
    silentField.add(element);
  }
  if (!needSubscription) {
    return;
  }

  if (isCollection) {
    collections.add(name);
  }
  // add stream
  subjects.add(name);
  classBuilder
    ..fields.add(
      Field(
        (builder) => builder
          ..late = true
          ..modifier = FieldModifier.final$
          ..name = name.subjectName
          ..assignment = Code('''
BehaviorSubject<$type>(
onListen: \$ref,
onCancel: \$unref,
)..add(\$src.$name)
'''),
      ),
    )
    ..methods.add(
      Method(
        (builder) => builder
          ..name = name.streamName
          ..returns = Reference('Stream<$type>')
          ..type = MethodType.getter
          ..body = Code(
            'return ${name.subjectName}.stream${isCollection ? '' : '.distinct()'};',
          ),
      ),
    );

  // add getter
  classBuilder.methods.add(
    Method(
      (builder) => builder
        ..annotations.add(CodeExpression(Code('override')))
        ..returns = Reference(type)
        ..type = MethodType.getter
        ..name = name
        ..body = Code('''
return ${name.subjectName}.value;
'''),
    ),
  );

  if (!hasSetter) {
    return;
  }

  classBuilder.methods.add(
    Method(
      (builder) => builder
        ..annotations.add(CodeExpression(Code('override')))
        ..type = MethodType.setter
        ..name = name
        ..requiredParameters.add(
          Parameter(
            (builder) => builder
              ..type = Reference(type)
              ..name = 'val'
              ..named = false,
          ),
        )
        ..body = Code('''
${name.subjectName}.add(val);
'''),
    ),
  );
}