2009-06-24 1 views
15

На данный момент я разрабатываю привязку на основе аннотаций для Java Swing, которая использует JGoodies Binding под капотом. К сожалению, я застрял в аннотации для привязки JRadioButton. Что я хочу сделать, это указать свойство-имя модели, которая содержит специальное значение (перечисление). Радиокнопка должна быть выбрана, если это свойство имеет определенное значение. Теперь я хочу, чтобы задать значение в аннотации, как это:Есть ли способ объявить атрибут аннотации для * any * enum?

@RadioButtonBinding(property = "selectedItem", selectedValue = MyEnum.FIRST) 
JRadioButton firstButton 

@RadioButtonBinding(property = "selectedItem", selectedValue = MyEnum.SECOND) 
JRadioButton secondButton 

Однако, я не знаю, как объявить аннотацию, чтобы разрешить выше и любой другой перечисление тоже. Моя первая догадка, но я узнал, что атрибуты аннотаций не могут быть универсальными:

@Documented 
@Retention(RetentionPolicy.RUNTIME) 
@Target(ElementType.FIELD) 
public @interface RadioButtonBinding { 

    /** The model-property to which the selected value is bound */ 
    String property(); 

    // Idea 1: Specifying the enum class and the enum constant as String - works but is not typesafe 

    Class<? extends Enum<?>> enumClass(); 

    String enumConstantName(); 

    // Idea 2: Directly specifying the enum constant - gives a compile-time error 

    <T extends Enum<T>> T enumValue(); 

} 

Любых идей, как решить эту проблему?

+0

Аннотации RadioButtonBinding, перечисленные здесь, включают в себя две идеи: Первый - указать класс Enum и константу String, которые будут использоваться из него. Но это, конечно, не типично и может привести к RuntimeExceptions. Второй - это указать значение перечисления напрямую, но это не работает. –

+0

btw Я много чего делал с JGoodies, одним из самых жалких времен, которые у меня были на Java. Самая большая проблема заключается в том, что у него есть «базовый» класс, который распространяется на большинство его других классов, и поэтому его методы имеют подписи, такие как метод (базовый, базовый, базовый), где «базовый» класс передается внутри, должен быть конкретным экземпляром, но подпись не дает вам никаких намеков относительно того, какой именно класс должен быть экземпляром. Часть привязок была хорошей идеей, но он не очень хорошо ее поддерживал в то время (годы назад), и она была незакончена и только задокументирована на немецком языке. –

ответ

3

Это не будет работать так, как вы этого хотите. Как вы узнали, вы можете использовать только обычные типы возврата в аннотациях. Кроме того, попытка обойти эти ограничения, делая такие вещи, как злоупотребление String, не будет работать, потому что вам нужно использовать константное выражение для инициализации значений аннотации.

Я думаю, что ближе всего вы собираетесь инициализировать строку, а затем использовать код для сравнения с именем enum(). Но там идет ваш тип безопасность ...

1

Если перечисления могут реализовать все тот же интерфейс, вы можете найти полезный этот вопрос «Coding tip - intersection types and java enums»

+0

К сожалению, нет, но благодарность за отзыв в любом случае. –

+0

Как именно вы используете этот общий интерфейс в атрибуте аннотации? ' & MyInterface> T enumValue();' не работает лучше, чем без интерфейса. – Imre

0

Я пытался решить эту проблему точно так же, и, насколько Я знаю, это невозможно. Это настоящий облом.

В моем случае я хотел указать аннотацию @Version, где можно использовать любое перечисление, а значения перечисления можно сравнить по порядковым номерам (чтобы найти порядок версий). Похоже, мне нужно делать то, что делают другие фреймворки (например, Guice, я думаю), и вместо этого использовать двойники; бит уродливый, но работает нормально при> = и < = проверяет.