Let act(p0, ... ,p(n-1)) be an action with n parameters.
Let PPM(p0, ... ,p(n-1)) be the pending-parameter-model that is negotiated with the interacting user by means of an action dialog in the UI. Through user interaction the PPM is filled with parameter values until all constraints are met and the action act can thus be invoked.
We can identify the parameter list PL {p0, ... ,p(n-1)} as (typed) n-tuple, with types t0, ... ,t(n-1)
The programming model provides 5 types of functions in support of the pending-parameter-model. For the sake of simplicity we say that each is a function PL -> ti, with ti being the type of the i-th parameter. For example given act(X x, Y y), we have default0Act(X x, Y y) -> X and default1Act(X x, Y y) -> Y
- defaulti
- autoCompletei
- choicesi
- disablei
- hidei
Now going through the negotiation process,
- let p[i] be the value of the i-th parameter of the PPM, and let PL be the parameter list {p[0], .. ,p[n-1]}
- let v[i] be the visibility flag of the i-th parameter (whether is rendered at all in the UI)
- let u[i] be the usability flag of the i-th parameter (whether can edit vs. being rendered read-only)
- let invalid[i] be the invalid message of the i-th parameter (only rendered when set)- let honor_constraints(PL) be a method that acts on the PPM and can modify its parameters PL- - any parameter that is constraint eg. by choices(PL) must be checked each time the PL changes- - if a parameter's value does fail the constraint check, it needs to be reset to its default value- - this in principle allows for developers to setup a situation, where parameters are validated and reset such that this process runs into an infinte loop, in other words the PL in theory migth not have a fixed point under given constraints, the framework needs to detect such cases at runtime and stop iterating the loop
def honor_constraints(PL):forEach i in 0..n-1if not choices_i(PL) contains p[i], thenp[i]:= default_i(PL)// detect infinite loops and stop with message 'Action parameter negotiation cannot yield a fixed point.'
1) Fill in defaults in two passes:
for i in 0..n-1 p[i]:= default_i() # no arg, init PL for i in 0..n-1 p[i]:= default_i(PL)
2) Process visibility and usability (disable/hide)
for i in 0..n-1 v[i]:= not hide_i(PL) u[i]:= not disable_i(PL)
3) Process individual parameter validity
// skip this step until (5) has been reached at least once! if step_5 was reached, then for i in 0..n-1 invalid[i]:= validate_i(PL)
4) Wait for user interaction,
- let reset_i be a user initiated reset request for the i-th parameter
- let update_i be a user initiated update for the i-th parameter, either triggered by direct entering of a value or using autoComplete or choices
on reset_i: p[i]:= default_i(PL) on update_i: p[i]:= the proposed new value as given by the update event on user initiates the action invocation goto (5) # process parameter-list validity goto (2) # start over
5) Process parameter-list validity
if validate(PL) is not empty, then render invocation veto message goto (4) # wait for user interaction
6) Invoke the action
act(PL)