Add KMeansClient RT support

nix
Owen Green 6 years ago
parent eb6aeb0304
commit b687b5649d

@ -92,6 +92,14 @@ struct IsModel<NRTThreadingAdaptor<ClientWrapper<T>>>
using type = typename ClientWrapper<T>::isModelObject; using type = typename ClientWrapper<T>::isModelObject;
}; };
template<typename T>
struct IsModel<ClientWrapper<T>>
{
using type = typename ClientWrapper<T>::isModelObject;
};
template<typename T> template<typename T>
using IsModel_t = typename IsModel<T>::type; using IsModel_t = typename IsModel<T>::type;

@ -1,16 +1,7 @@
FluidKMeans : FluidManipulationClient { FluidKMeans : FluidDataClient {
var <>k; var <>k;
*new {|server|
var uid = UniqueID.next;
^super.new(server,uid)!?{|inst|inst.init(uid);inst}
}
init {|uid|
id = uid;
}
fit{|dataset,k, maxIter = 100, action| fit{|dataset,k, maxIter = 100, action|
this.k = k; this.k = k;
this.prSendMsg(\fit, this.prSendMsg(\fit,

@ -9,6 +9,7 @@ FluidProxyUgen : UGen {
init { |pluginname...args| init { |pluginname...args|
this.pluginname = pluginname; this.pluginname = pluginname;
inputs = args++Done.none++0; inputs = args++Done.none++0;
rate = inputs.rate;
} }
name{ name{
@ -50,17 +51,23 @@ FluidManipulationClient {
^super.newCopyArgs(server ?? {Server.default}).baseinit(*args) ^super.newCopyArgs(server ?? {Server.default}).baseinit(*args)
} }
makeDef { |defName...args|
^SynthDef(defName,{
var ugen = FluidProxyUgen.kr(this.class.name, *args);
this.ugen = ugen;
ugen
});
}
updateSynthControls {}
baseinit { |...args| baseinit { |...args|
var makeFirstSynth,synthMsg; var makeFirstSynth,synthMsg;
id = UniqueID.next; id = UniqueID.next;
postit = {|x| x.postln;}; postit = {|x| x.postln;};
keepAlive = true; keepAlive = true;
defName = (this.class.name.asString ++ id).asSymbol; defName = (this.class.name.asString ++ id).asSymbol;
def = SynthDef(defName,{ def = this.makeDef(defName,*args);
var ugen = FluidProxyUgen.kr(this.class.name, *args);
this.ugen = ugen;
ugen
});
synth = Synth.basicNew(def.name, server); synth = Synth.basicNew(def.name, server);
synthMsg = synth.newMsg(RootNode(server)); synthMsg = synth.newMsg(RootNode(server));
def.doSend(server,synthMsg); def.doSend(server,synthMsg);
@ -70,10 +77,12 @@ FluidManipulationClient {
if(keepAlive){ if(keepAlive){
synth = Synth(defName,target: RootNode(server)); synth = Synth(defName,target: RootNode(server));
synth.onFree{clock.sched(0,onSynthFree)}; synth.onFree{clock.sched(0,onSynthFree)};
this.updateSynthControls;
} }
}; };
CmdPeriod.add({synth = nil}); CmdPeriod.add({synth = nil});
synth.onFree{clock.sched(0,onSynthFree)}; synth.onFree{clock.sched(0,onSynthFree)};
this.updateSynthControls;
} }
free{ free{
@ -118,6 +127,71 @@ FluidManipulationClient {
} }
} }
FluidDataClient : FluidManipulationClient {
var <id;
var <inBus, <outBus;
var <inBuffer, <outBuffer;
*new {|server,inbus, outbus,inbuf,outbuf|
var uid = UniqueID.next;
^super.new(server,uid)!?{|inst|
inst.init(uid);
inst.inBus = inbus;
inst.outBus = outbus;
inst.inBuffer = inbuf;
inst.outBuffer = outbuf;
inst
}
}
updateSynthControls{
synth !? {
if(synth.isRunning){
synth.set(
\in, inBus !? {inBus.index} ?? {0},
\out, outBus !? {outBus.index} ?? {0},
\inBuffer,inBuffer !? {inBuffer.asUGenInput} ?? {-1},
\outBuffer,outBuffer !? {outBuffer.asUGenInput} ?? {-1}
) }
};
}
inBuffer_{|newBuffer|
inBuffer = newBuffer;
this.updateSynthControls;
}
outBuffer_{|newBuffer|
outBuffer = newBuffer;
this.updateSynthControls;
}
init {|uid|
id = uid;
}
inBus_{ |newBus|
inBus = newBus;
this.updateSynthControls;
}
outBus_{ |newBus|
outBus = newBus;
this.updateSynthControls;
}
makeDef{|defName...args|
^SynthDef(defName, { |in,out,inBuffer,outBuffer|
var ugen = FluidProxyUgen.kr(this.class.name, T2A.ar(T2K.kr(In.ar(in))), inBuffer, outBuffer, *args);
this.ugen = ugen;
Out.kr(out,ugen);
ugen
});
}
}
FluidServerCache { FluidServerCache {
var cache; var cache;

@ -101,7 +101,6 @@ fork{
} }
}); });
// Cols of kmeans should match dataset, size is the number of clusters // Cols of kmeans should match dataset, size is the number of clusters
~kmeans.cols; ~kmeans.cols;
~kmeans.size; ~kmeans.size;
@ -141,4 +140,36 @@ w.refresh;
w.front; w.front;
) )
//Querying on the server using busses and buffers:
//This is the equivalent of predictPoint, but wholly on the server
//FluidKMeans is accessed via its own synth, so we need to use
//a bus to communicate with it. The inBus receives a trigger to query, using data
//from inBuffer; a trigger is then send to outBus with the prediction in outBuffer
(
~ib = Bus.audio(s); // input bus must be audio (for now)
~ob = Bus.control(s); //output bus can be kr
~inpPoint = Buffer.alloc(s,2);
~outPoint = Buffer.alloc(s,1);
//Set properties on FluidKMeans:
~kmeans.inBus_(~ib).outBus_(~ob).inBuffer_(~inpPoint).outBuffer_(~outPoint);
)
//We make two Synths. One, before FluidKMeans, generates a random point and sends
//a trigger to query. The second, after FluidKMeans, gives us the predicted cluster //triggering upadtes from the outBus
(
//pitching
{
var trig = Impulse.ar(10);
var point = [WhiteNoise.kr,WhiteNoise.kr];
BufWr.kr(point[0],~inpPoint,0);
BufWr.kr(point[1],~inpPoint,1);
Poll.kr(T2K.kr(trig),point,[\pointX,\pointY]);
Out.ar(~ib.index,[trig]);
}.play(~kmeans.synth,addAction:\addBefore);
//catching
{
Poll.kr(In.kr(~ob),Latch.kr(BufRd.kr(1,~outPoint,0,interpolation:0),In.kr(~ob)),\cluster);
}.play(~kmeans.synth,addAction:\addAfter);
)
:: ::

@ -26,7 +26,7 @@ PluginLoad(FluidSTFTUGen)
makeSCWrapper<NRTThreadedDataSetQueryClient>("FluidDataSetQuery",ft); makeSCWrapper<NRTThreadedDataSetQueryClient>("FluidDataSetQuery",ft);
makeSCWrapper<NRTThreadedLabelSetClient>("FluidLabelSet",ft); makeSCWrapper<NRTThreadedLabelSetClient>("FluidLabelSet",ft);
makeSCWrapper<NRTThreadedKDTreeClient>("FluidKDTree",ft); makeSCWrapper<NRTThreadedKDTreeClient>("FluidKDTree",ft);
makeSCWrapper<NRTThreadedKMeansClient>("FluidKMeans",ft); makeSCWrapper<RTKMeansClient>("FluidKMeans",ft);
makeSCWrapper<NRTThreadedKNNClassifierClient>("FluidKNNClassifier",ft); makeSCWrapper<NRTThreadedKNNClassifierClient>("FluidKNNClassifier",ft);
makeSCWrapper<NRTThreadedKNNRegressorClient>("FluidKNNRegressor",ft); makeSCWrapper<NRTThreadedKNNRegressorClient>("FluidKNNRegressor",ft);
makeSCWrapper<NRTThreadedNormalizeClient>("FluidNormalize",ft); makeSCWrapper<NRTThreadedNormalizeClient>("FluidNormalize",ft);

Loading…
Cancel
Save