1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111
|
SimpleController {
var model, actions;
// responds to updates of a model
*new { arg model;
^super.newCopyArgs(model).init
}
init {
model.addDependant(this);
}
put { arg what, action;
if (actions.isNil, {
actions = IdentityDictionary.new(4);
});
actions.put(what, action);
}
update { arg theChanger, what ... moreArgs;
var action;
if(actions.notNil) {
action = actions.at(what);
if (action.notNil, {
action.valueArray(theChanger, what, moreArgs);
});
};
}
remove {
model.removeDependant(this);
}
removeAt{ |what|
if (actions.notNil) {
actions.removeAt(what)
}
}
}
TestDependant {
update { arg thing;
(thing.asString ++ " was changed.\n").post;
}
}
NotificationCenter {
classvar registrations;
// who \didSomething
*notify { arg object, message, args;
registrations.at(object,message).copy.do({ arg function;
function.valueArray(args)
})
}
// who \didSomething
*register { arg object,message,listener,action;
var nr;
nr = NotificationRegistration(object,message,listener);
registrations.put(object,message,listener,action);
^nr;
}
*unregister { arg object,message,listener;
var lastKey,lastDict;
lastDict = registrations.at(object,message);
if(lastDict.notNil,{
lastDict.removeAt(listener);
(lastDict.size == 0).if({
registrations.removeAt(object,message);
(registrations.at(object).size == 0).if({
registrations.removeAt(object);
});
});
});
}
*registerOneShot { arg object,message,listener,action;
var nr;
nr = NotificationRegistration(object,message,listener);
registrations.put(object,message,listener,
{ |args|
action.value(args);
this.unregister(object,message,listener)
});
^nr
}
*clear {
registrations = MultiLevelIdentityDictionary.new;
}
*registrationExists { |object,message,listener|
^registrations.at(object,message,listener).notNil
}
*initClass {
this.clear
}
*removeForListener { |listener|
registrations.removeAt(listener)
}
}
NotificationRegistration {
var <>object,<>message,<>listener;
*new { arg o,m,l;
^super.new.object_(o).message_(m).listener_(l)
}
remove {
NotificationCenter.unregister(object,message,listener)
}
}
|