from http://www.cs.chalmers.se/~magnus/GuiFest-95/postchallenge.html
The "Multiple Counter" program shows a counter
which can be incremented manually or periodically. The counter
can at any time be copied, giving a new counter with its own
independent state, which is copied from the old counter in the
very moment of creation. A counter can also be linked, giving a
new view to the same counter. One can think of the copying and
linking as being analogous to ln
and cp
applied to files under Unix.
A counter view looks something like this:
+------------+ | | | +--------+ | | | 0 | | | +--------+ | | | | | | +--------+ | | | Manual | | | +--------+ | | | | +--------+ | | | Auto | | | +--------+ | | | | +--------+ | | | Copy | | | +--------+ | | | | +--------+ | | | Link | | | +--------+ | +------------+
It contains the following elements:
If possible, it should be possible to distinguish counters that are linked - eg. links have the same background colour or window title, copies have a different colour or title, or perhaps by layout - links placed across the screen, copies placed down the screen.
A solution in fudgets, and one in K.
A counter is either a copy of an existing counter, or a link to one.
When the copy button of a counter C is pressed, the following operations are performed:
When count[i] changes, D updates itself from count[i]; when D changes, it updates count[i] with its new value.
When the link button of a counter C is pressed, the following operation is performed:
If D is linked from C, then both D and C depend on count[i]: if either changes, count[i] is updated, and so the other link will update itself from count[i].
Let's step through the code.
Initialize the count variable:
count:()
p0 is a dictionary containing five variables:
p0.value 0 p0.auto 0 p0.manual code which increments value p0.copy code which calls the copy functiuon with a symbol of its dictionary p0.link code which calls the copy function with a symbol of its dictionary
p0[`value`auto`manual`copy`link]:(0;0;"value+:1";".k.copy _d";".k.link _d")
Classify the variables in p0:
p0[.;`c]:`data`check`button`button`button
value is a data widget, auto is a checkbutton, manual, copy, and link are buttons.
p0..l:$I:0
I, initialized to 0, is incremented whenever a new counter is manufactured. p0's label is "0".
copy:{`show$~@[~new[];`d`t`l;:;(".k.count ",i;".k.count[",i,";_i]:_v ._i";i:$-1+#count,:. x)]}
The copy function contains one line of code, and has the form:
`show$~@[x;y;:;z]
A new counter-name is generated. Its dependency, trigger, and label attributes are defined. Input to the function x is the counter whose copy button was pressed; that counter is appended to count.
link:{`show$~.[~new[];();:;.~x]}
The link function. The function contains one line of code, and has the same form as copy, except that it is much simpler. A new counter is created, and its value is the counter x which is input to the link function.
new:{`$".k.p",$I+:1}
The new function. Make a new counter name by incrementing I and appending it to ".k.p".
.t..t:"{if[.k.count[x;`auto];.k.count[x;`value]+:1]}'!#.k.count;" \t 1
Every second the timer .t is updated with the current time. The timer trigger checks each counter to see if auto is on. If so, it increments its value.
copy`.k.p0
Kick things off by making a copy of the counter template p0.
Example: