Have started to make it possible to make a ui described in one or more xml files to be connected (bound) to code in a (java) application. There are two kinds of relationship currently envisaged:
- simple callbacks representing a one-way execution of code from the ui
for example, code that is invoked when a button is pressed
- variables representing a two-way relationship of code to the ui
for example, a slider that not only controls some feature of the application (e.g. the gravity slider in constructor), but might itself respond (“listen”) to changes in the application, as in the selected slider in the constructor application is indicated simultateously in both the main simulation window and in the sinewave window on the left. In a new version of the constructor application there might be sliders (or even just numeric editors) that can control the position (x and y values) of the selected mass and also reflect changes in its position.
These I’m calling bindings and the main package providing binding services is net.playforge.ui.bindings. The basic way to mark in the java code of the application that a particular binding point is “advertised” (in other words part of that application’s “playforge-API” is by ”annotations” (using java 1.5 annotations) the relevant methods with
@Callable(name="whatever’) (for callbacks) and
@Variable(name="whatever") (for variables, more required here – the return type must implement PlayforgeVariable). (There are some other thoughts on this – it might be possible to go around the playforge API and call java methods directly, there also might be other ways of creating PlayforgeVariables dynamically (through annotating multiple methods) but this isn’t immediately planned in).
This is mostly straightforward, but gets a bit more tricky if you want to access something which is not in the application class, but in a different class that the application “knows how” to navigate to… for example in the example given above the
selectedMass.location.x. These kind of compound names need to be split into a chain of calls, starting at the application, and each one then introspected (using a playforge specificic introspector – in net.playforge.introspection) but the whole thing managed by the Name Binding Manager in net.playforge.ui.bindings.
Variables themselves get more tricky, especially when you consider that a chain of variable calls (like
selectedMass.location.x) needs to be updated not just when
x changes, but also when
selectedMass changes… (and to further complicate this somewhat artificial example, note that
location probably doesn’t need to be a variable, but a callable…. (it won’t actually change for the life of that mass). Obviously another way to do this is to make a specific variable available on the application ”
selectedMassLocationX” but this would be ugly and hard to program, so we would not want to force application developers to go down this route.