All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.airbnb.epoxy.processor.StringOverloadWriter.kt Maven / Gradle / Ivy

package com.airbnb.epoxy.processor

import androidx.annotation.NonNull
import androidx.annotation.Nullable
import androidx.annotation.PluralsRes
import androidx.annotation.StringRes
import com.airbnb.epoxy.processor.GeneratedModelWriter.Companion.addOnMutationCall
import com.airbnb.epoxy.processor.GeneratedModelWriter.Companion.addParameterNullCheckIfNeeded
import com.airbnb.epoxy.processor.GeneratedModelWriter.Companion.setBitSetIfNeeded
import com.squareup.javapoet.ArrayTypeName
import com.squareup.javapoet.CodeBlock
import com.squareup.javapoet.MethodSpec
import com.squareup.javapoet.MethodSpec.Builder
import com.squareup.javapoet.ParameterSpec
import com.squareup.javapoet.TypeName
import java.util.ArrayList
import javax.lang.model.element.Modifier.PUBLIC

internal class StringOverloadWriter(
    private val modelInfo: GeneratedModelInfo,
    private val attr: AttributeInfo,
    private val configManager: ConfigManager
) {
    private val fieldName: String = attr.fieldName
    private val nullable: Boolean = attr.isNullable == true

    fun buildMethods(): List {
        val methods = ArrayList()
        methods.add(buildGetter())

        methods.add(finishSetter(buildCharSequenceSetter(baseSetter())))
        methods.add(finishSetter(buildStringResSetter(baseSetter())))
        methods.add(finishSetter(buildStringResWithArgsSetter(baseSetter())))
        methods.add(finishSetter(buildQuantityStringResSetter(baseSetter("QuantityRes"))))

        return methods
    }

    private fun buildCharSequenceSetter(builder: Builder): Builder {
        val paramName = attr.generatedSetterName()
        val paramBuilder = ParameterSpec.builder(CharSequence::class.java, paramName)

        if (nullable) {
            paramBuilder.addAnnotation(Nullable::class.java)
        } else {
            paramBuilder.addAnnotation(NonNull::class.java)
        }

        addJavaDoc(builder, false)

        builder.addParameter(paramBuilder.build())

        addParameterNullCheckIfNeeded(configManager, attr, paramName, builder)
        builder.addStatement("\$L.setValue(\$L)", fieldName, paramName)

        return builder
    }

    private fun buildStringResSetter(builder: Builder): Builder {
        builder.addParameter(
            ParameterSpec.builder(TypeName.INT, STRING_RES_PARAM)
                .addAnnotation(StringRes::class.java)
                .build()
        )

        addJavaDoc(builder, true)
        builder.addStatement("\$L.setValue(\$L)", fieldName, STRING_RES_PARAM)

        return builder
    }

    private fun buildStringResWithArgsSetter(builder: Builder): Builder {
        builder.addParameter(
            ParameterSpec.builder(TypeName.INT, STRING_RES_PARAM)
                .addAnnotation(StringRes::class.java)
                .build()
        )

        addJavaDoc(builder, true)

        builder
            .addParameter(
                ParameterSpec.builder(
                    ArrayTypeName.of(TypeName.OBJECT),
                    ARGS_PARAM
                ).build()
            )

        builder.addStatement("\$L.setValue(\$L, \$L)", fieldName, STRING_RES_PARAM, ARGS_PARAM)
            .varargs()

        return builder
    }

    private fun buildQuantityStringResSetter(builder: Builder): Builder {

        builder.addParameter(
            ParameterSpec.builder(TypeName.INT, PLURAL_RES_PARAM)
                .addAnnotation(PluralsRes::class.java)
                .build()
        )

        addJavaDoc(builder, true)

        builder.addParameter(ParameterSpec.builder(TypeName.INT, QUANTITY_PARAM).build())

        builder
            .addParameter(
                ParameterSpec.builder(
                    ArrayTypeName.of(TypeName.OBJECT),
                    ARGS_PARAM
                ).build()
            )

        builder.addStatement(
            "\$L.setValue(\$L, \$L, \$L)", fieldName, PLURAL_RES_PARAM,
            QUANTITY_PARAM,
            ARGS_PARAM
        )
            .varargs()

        return builder
    }

    private fun baseSetter(suffix: String = ""): Builder {
        val name = attr.generatedSetterName() + suffix

        val builder = MethodSpec.methodBuilder(name)
            .addModifiers(PUBLIC)
            .returns(modelInfo.parameterizedGeneratedName)

        addOnMutationCall(builder)
        setBitSetIfNeeded(modelInfo, attr, builder)
        return builder
    }

    private fun addJavaDoc(
        builder: Builder,
        forStringRes: Boolean
    ) {
        if (attr.javaDoc == null) {
            return
        }

        val javaDoc = CodeBlock.builder()

        if (forStringRes) {
            if (attr.isRequired) {
                javaDoc.add("Throws if a value <= 0 is set.\n

\n") } else { javaDoc.add( "If a value of 0 is set then this attribute will revert to its " + "default value.\n

\n" ) } } builder.addJavadoc(javaDoc.add(attr.javaDoc).build()) } private fun buildGetter(): MethodSpec { val getterName = attr.generatedGetterName( isOverload = modelInfo.isOverload(attr) ) val builder = MethodSpec.methodBuilder(getterName) .addModifiers(PUBLIC) .returns(CharSequence::class.java) if (nullable) { builder.addAnnotation(Nullable::class.java) } return builder .addAnnotations(attr.getterAnnotations) .addParameter(ClassNames.ANDROID_CONTEXT, "context") .addStatement("return \$L", fieldName + ".toString(context)") .build() } companion object { private val PLURAL_RES_PARAM = "pluralRes" private val STRING_RES_PARAM = "stringRes" private val ARGS_PARAM = "formatArgs" private val QUANTITY_PARAM = "quantity" private fun finishSetter(builder: MethodSpec.Builder): MethodSpec { return builder .addStatement("return this") .build() } } }





© 2015 - 2024 Weber Informatics LLC | Privacy Policy