Kotlin Аннотация IntDef

У меня есть этот пример кода:

class MeasureTextView: TextView {
    constructor(context: Context?) : super(context)
    constructor(context: Context?, attrs: AttributeSet?) : super(context, attrs)
    constructor(context: Context?, attrs: AttributeSet?, defStyleAttr: Int) : super(context, attrs, defStyleAttr)
    constructor(context: Context?, attrs: AttributeSet?, defStyleAttr: Int, defStyleRes: Int) : super(context, attrs, defStyleAttr, defStyleRes)

    companion object{
        val UNIT_NONE = -1
        val UNIT_KG = 1
        val UNIT_LB = 0            
    }

    fun setMeasureText(number: Float, unitType: Int){

        val suffix = when(unitType){
            UNIT_NONE -> {
                EMPTY_STRING
            }
            UNIT_KG -> {
                KG_SUFIX
            }
            UNIT_LB -> {
                LB_SUFIX
            }
            else -> throw IllegalArgumentException("Wrong unitType passed to formatter: MeasureTextView.setMeasureText")
        }

        // set the final text
        text = "$number $suffix"
    }
}

Я хочу использовать во время компиляции функцию автоматического завершения в сочетании с аннотацией IntDef, поэтому, когда я вызываю setMeasureText(...), статические переменные отображаются как параметры аргумента этого метода.

Я искал об этом, и я не смог найти, поддерживает ли Kotlin эти аннотации в стиле java (например, intdef). Поэтому я попробовал это и сделал аннотацию для этого, но он не будет показан в автозавершении.

Мой вопрос: - Поддерживается ли Java-аннотация IntDef в Kotlin (последняя версия)

  • Если это так, как я могу включить ON в Android Studio IDE (если он работает, я не могу заставить компилятор предложить его).

  • Если это не так, есть ли какой-либо метод Kotlin, чтобы сделать это время проверки компиляции

Ответ 1

Как и в Kotlin 1.0.3, аннотация @IntDef не поддерживается, но поддержка планируется для более поздних версий.

Способ Kotlin для выполнения этих проверок времени компиляции заключается в использовании enum class вместо последовательности констант Int.

Ответ 2

Странная вещь, но этот вопрос приходит в поиск раньше того же самого с правильным ответом

Копирование здесь:

import android.support.annotation.IntDef
public class Test {

    companion object {

         @IntDef(SLOW, NORMAL, FAST)
         @Retention(AnnotationRetention.SOURCE)
         annotation class Speed

         const val SLOW = 0
         const val NORMAL = 1
         const val FAST = 2
    }

    @Speed
    private var speed: Int=SLOW

    public fun setSpeed(@Speed speed: Int) {
        this.speed = speed
    }
}

Ответ 3

Если вы вызываете setMeasureText из Java, вы можете заставить его работать, создав свой IntDef в Java тоже

// UnitType.java
@Retention(RetentionPolicy.SOURCE)
@IntDef({MeasureText.UNIT_KG, MeasureText.UNIT_LB, MeasureText.UNIT_NONE})
public @interface UnitType {}

h/t Tonic Artos

Вам также потребуется обновить свой объект-компаньон, чтобы сделать ваши значения длинными и общедоступными

companion object{
    const val UNIT_NONE = -1L
    const val UNIT_KG = 1L
    const val UNIT_LB = 0L
}

Ответ 4

Мой предпочтительный способ использовать IntDef с Kotlin - использовать объявления верхнего уровня:

package com.example.tips


const val TIP_A = 1
const val TIP_B = 2
const val TIP_C = 3

@IntDef(TIP_A, TIP_B, TIP_C)
@Retention(AnnotationRetention.SOURCE)
annotation class TipId


class TipsDataProvider {

    fun markTip(@TipId tipId: Int) {
    ...
    }
}

Никаких дополнительных классов или объектов не требуется! Подробнее о объявлениях верхнего уровня здесь.

Ответ 5

Как сказано в принятом ответе, используйте enum class в kotlin.

Я написал специальный код задаваемого вопроса, он может помочь некоторым новичкам в kotlin:

class MeasureTextView: TextView {
   enum class UnitType(val value : Int){
       UNIT_NONE(-1),
       UNIT_KG(0),
       UNIT_LB(1)
   }

   fun setMeasureText(number: Float, unitType: UnitType){
       val suffix = unitType.value
   }
}