简体   繁体   中英

Make custom forms with annotations in Java

I'm trying to make custom forms with annotations. My idea is that given an annotated class, my code could generate a FX GUI form to edit objects of that class. It should be clearer in the code:

@...
@interface Form {
  String label() default "";
}

@Form
class SomeData {
  @Form(label="Name")
  String name;
  @Form(label="Age")
  int age;
  ...
}

class FormBuilder {
  Pane makeForm(Class annotated) {
    Pane pane = ... ;
    for (/*each annotated field*/) {
      Label label = new Label(/*field's annotated label*/));
      Control field = generateControl(/*annotated field's type*/));
      ...
      pane.getChildren().addAll(label, field);
    }
    return pane;
  }

  Control generateControl(Class type) {
    // returns the control that matches with the type
    // its everything OK here
  }

  main(...) {
    Pane someDataForm = makeForm(SomeData.class);
    ...
  }
}

I am starting in custom annotations now, and didn't get yet how to:

  • Iterate over annotated fields of an annotated class
  • Get its annotated data ( label :String)
  • Get annotated field's type (name: String and age: Integer in this case)

in order to implement the method makeForm

Before we get to reflections code, I think you're going to need another annotation to represent your classes that represent a custom form. Your current @Form annotation is better suited at the field level, since it's representing the label for each form field. I would rename this to @FormField . Then, your @Form annotation can just be used to tell the reflections API which classes are custom forms.

Now, on to the code. First, you'll need to initialize reflections within your application. The package will be the first package where you want to utilize reflection in your app.

private static Reflections reflections = new Reflections("your.java.package");

To get every class annotated with your @Form annotation, you can use:

Set<Class<? extends Forms>> customForms = reflections.getTypesAnnotatedWith(Form.class)

Now, you can loop through each custom form, and parse through the annotations of each field:

// Loop through every class with Form annotation
    for (Class<? extends Forms> form : customForms) {
        for (Field field : form.getDeclaredFields()) {
            // Check each field, if it has your FormField attribute, you can then access the annotation methods
            if (field.isAnnotationPresent(FormField.class)) {
                Label label = new Label(field.getAnnotation(FormField.class).label());
                // Do additional stuff to build your form
            }
        }
    }

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM