Created
December 11, 2012 20:32
-
-
Save frankleonrose/4261903 to your computer and use it in GitHub Desktop.
Simple class to create a set of controlP5.Slider controllers from a POJO with setValueName(<Numeric Type>) methods. Optional Range annotation and getting of default value.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// I ran into a weird unknown method invocation with cp5magic (perhaps because I have to use Processing 1.5.1 because of bugs in 2.0b). | |
// That combined with having classes with setParamName1(numeric) style setters, I wrote this. Enjoy. | |
/* | |
Usage: | |
public class MyParameterClass { | |
double myParameter = 100d; | |
@Range(max=200) | |
public void setMyParameter(double v) { myParameter = v; } | |
public double getMyParameter() { return myParameter; } | |
// Any number of other params, same structure… | |
// Only the setter method is required | |
} | |
MyParameterClass myParams = new MyParameterClass(); | |
ParameterView pv = new ParameterView(cp5); | |
pv.createControllers(myParams); | |
*/ | |
import java.lang.annotation.Retention; | |
import java.lang.annotation.RetentionPolicy; | |
import java.lang.reflect.InvocationTargetException; | |
import java.lang.reflect.Method; | |
import java.security.InvalidParameterException; | |
import controlP5.ControlEvent; | |
import controlP5.ControlListener; | |
import controlP5.ControlP5; | |
import controlP5.ControlWindow; | |
import controlP5.ControllerGroup; | |
import controlP5.Slider; | |
import controlP5.Tab; | |
public class ParameterView { | |
@Retention(RetentionPolicy.RUNTIME) | |
public @interface Range { | |
float min() default 0f; | |
float max(); | |
} | |
private ControlP5 cp5; | |
private int width; | |
private int controlY = 0; | |
private ControlWindow window; | |
public ParameterView(final ControlP5 cp5) { | |
this.cp5 = cp5; | |
this.width = 400; | |
window = cp5.controlWindow; | |
// cp5.addControlWindow("Parameter Window", 100, 100, 400, 600) | |
// .hideCoordinates().setBackground(0); | |
cp5.addBang("Save Properties").addListener(new ControlListener() { | |
@Override | |
public void controlEvent(ControlEvent theEvent) { | |
cp5.saveProperties(); | |
} | |
}); | |
} | |
public void createControllers(final Object pojo) { | |
Tab tab = cp5.addTab(window, pojo.getClass().getSimpleName()); | |
ControllerGroup<?> group = cp5.begin(window); | |
controlY = 0; | |
for (final Method setter : pojo.getClass().getMethods()) { | |
if (setter.getName().startsWith("set")) { | |
@SuppressWarnings("rawtypes") | |
final Class parameterClass = getNumericParameter(setter); | |
if (parameterClass != null) { | |
float min = 0; | |
float max = 100; | |
float defalt = 50; | |
try { | |
Method getter = pojo.getClass().getMethod( | |
setter.getName().replace("set", "get")); | |
Object val = getter.invoke(pojo); | |
if (val instanceof Number) { | |
defalt = ((Number) val).floatValue(); | |
// Make sure range includes default... | |
max = Math.max(max, defalt); | |
min = Math.min(min, defalt); | |
} | |
} catch (SecurityException e1) { | |
// TODO Auto-generated catch block | |
e1.printStackTrace(); | |
} catch (NoSuchMethodException e1) { | |
// Possible... | |
} catch (IllegalArgumentException e) { | |
// TODO Auto-generated catch block | |
e.printStackTrace(); | |
} catch (IllegalAccessException e) { | |
// TODO Auto-generated catch block | |
e.printStackTrace(); | |
} catch (InvocationTargetException e) { | |
// TODO Auto-generated catch block | |
e.printStackTrace(); | |
} | |
Range a = setter.getAnnotation(Range.class); | |
if (a!=null) { | |
min = a.min(); | |
max = a.max(); | |
// Ensure that defalt is within min<=defalt<=max | |
defalt = Math.min(defalt, max); | |
defalt = Math.max(min, defalt); | |
} | |
String label = setter.getName().replace("set", ""); | |
Slider slider = cp5.addSlider(label) | |
.setLabelVisible(true) | |
.setPosition(0, controlY += 20) | |
.setSize(width / 2, 20) | |
.setRange(min, max) | |
.setValue(defalt) | |
.setGroup(group) | |
.setTab(tab.getName()); | |
slider.addListener(new ControlListener() { | |
@Override | |
public void controlEvent(ControlEvent theEvent) { | |
try { | |
if (parameterClass == Integer.class | |
|| parameterClass == Integer.TYPE) { | |
int val = (int) theEvent.getValue(); | |
setter.invoke(pojo, val); | |
} | |
else if (parameterClass == Double.class | |
|| parameterClass == Double.TYPE) { | |
double val = theEvent.getValue(); | |
setter.invoke(pojo, val); | |
} | |
else if (parameterClass == Float.class | |
|| parameterClass == Float.TYPE) { | |
float val = theEvent.getValue(); | |
setter.invoke(pojo, val); | |
} | |
else { | |
throw new InvalidParameterException( | |
"Cannot handle parameter type " | |
+ parameterClass); | |
} | |
} catch (IllegalArgumentException e) { | |
// TODO Auto-generated catch block | |
e.printStackTrace(); | |
} catch (IllegalAccessException e) { | |
// TODO Auto-generated catch block | |
e.printStackTrace(); | |
} catch (InvocationTargetException e) { | |
// TODO Auto-generated catch block | |
e.printStackTrace(); | |
} | |
} | |
}); | |
} | |
} | |
} | |
cp5.end(); | |
} | |
@SuppressWarnings("rawtypes") | |
private Class getNumericParameter(Method m) { | |
if (m.getParameterTypes().length != 1) { | |
return null; | |
} | |
// @SuppressWarnings("rawtypes") | |
Class pc = m.getParameterTypes()[0]; | |
if (pc.getSuperclass() == Number.class) { | |
return pc; | |
} | |
if (pc == Double.TYPE || pc == Float.TYPE || pc == Integer.TYPE | |
|| pc == Long.TYPE) { | |
return pc; | |
} | |
return null; | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment