In Java, we have generics and Generic arguments may be specified to have to extends/implement a certain class/interface.
class MyClass<T extends Number>
One can also specify that it has to implement several interfaces
class MyClass<T extends Number & Comparable>
My question is; how can I specify that a generic argument must extend one of two classes?
Class MyClass<T extends JComponent OR JFrame>
What I have is a Propery
class, which at this time look like this.
public abstract class Property<T> {
public abstract void set(JComponent component, T value);
public abstract void set(JFrame component, T value);
public abstract T get(JComponent component);
public abstract T get(JFrame component);
public static Property<Integer> HEIGHT = new Property<Integer>() {
@Override
public void set(JComponent component, Integer value) {
component.setSize(component.getWidth(), value);
}
@Override
public Integer get(JComponent component) {
return component.getHeight();
}
@Override
public void set(JFrame component, Integer value) {
component.setSize(component.getWidth(), value);
}
@Override
public Integer get(JFrame component) {
return component.getHeight();
}
};
public static Property<Integer> WIDTH = new Property<Integer>() {
@Override
public void set(JComponent component, Integer value) {
component.setSize(value, component.getHeight());
}
@Override
public Integer get(JComponent component) {
return component.getWidth();
}
@Override
public void set(JFrame component, Integer value) {
component.setSize(value, component.getHeight());
}
@Override
public Integer get(JFrame component) {
return component.getWidth();
}
};
...
}
Although, more properties, like BACKGROUND_COLOR, and LOCATION.
The problem really starts here, as you may be able to se the duplicate code for every property, but it gets worse in the Animation class:
public class Animation {
public static void callbackAnimation(AnimationCallback callback, double duration, double fps) {
double timeout = (1/fps)*1000;
int iterations = (int)(duration/timeout);
for (int i = 0; i <= iterations; i++) {
callback.run((double)i/(double)iterations);
try {
Thread.sleep((long)timeout);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
public static void animateProperty(final JComponent component, final Property<Color> property, Color to, double duration, double fps) {
final Color currentValue = property.get(component);
final int differenceRed = to.getRed() - currentValue.getRed();
final int differenceGreen = to.getGreen() - currentValue.getGreen();
final int differenceBlue = to.getBlue() - currentValue.getBlue();
final int differenceAlpha = to.getAlpha() - currentValue.getAlpha();
Animation.callbackAnimation(new AnimationCallback() {
@Override
public void run(double fraction) {
Color newColor = new Color(
(int)(currentValue.getRed()+(differenceRed*fraction)),
(int)(currentValue.getGreen()+(differenceGreen*fraction)),
(int)(currentValue.getBlue()+(differenceBlue*fraction)),
(int)(currentValue.getAlpha()+(differenceAlpha*fraction))
);
property.set(component, newColor);
}
}, duration, fps);
}
public static void animateProperty(final JFrame component, final Property<Color> property, Color to, double duration, double fps) {
final Color currentValue = property.get(component);
final int differenceRed = to.getRed() - currentValue.getRed();
final int differenceGreen = to.getGreen() - currentValue.getGreen();
final int differenceBlue = to.getBlue() - currentValue.getBlue();
final int differenceAlpha = to.getAlpha() - currentValue.getAlpha();
Animation.callbackAnimation(new AnimationCallback() {
@Override
public void run(double fraction) {
Color newColor = new Color(
(int)(currentValue.getRed()+(differenceRed*fraction)),
(int)(currentValue.getGreen()+(differenceGreen*fraction)),
(int)(currentValue.getBlue()+(differenceBlue*fraction)),
(int)(currentValue.getAlpha()+(differenceAlpha*fraction))
);
property.set(component, newColor);
}
}, duration, fps);
}
}
I stripped out some methods, but you should get the idé. I have to write every single method twice, once for JFrame and once for JComponent, which is a pain.