27. Environment

Environments 와 Events는 patterns을 위한 상징적인 event framework를 세우기 위해 사용되며, pattern을 사용한 composition을 컨트롤 하도록 한다. 

-Environment

Environment 는 IdentityDictionary으로 symbol들을 value들로 맵핑한다. 
언제나 하나의 current Environment가 존재하여 class Object의 currentEnvironment class variable에 저장된다.

Symbol 과 value는 다음과 같이 하나의 짝으로 current Environment에 저장된다.:

currentEnvironment.put(myvariable, 999);

다시 symbol에 저장된 값을 보고 싶다면 다음과 같이 출력한다.

currentEnvironment.at(myvariable).postln;

맨위에 있는 것을 다음과 같이 간단하게 쓸 수 있다. :

~myvariable = 888;

또한 값을 확인하려면:

~myvariable.postln;


-Environment 만들기

Environment는 class method “make”로 만들어 진다. 그리고 그 안에 값을 저장한다. 
make가 하는일은 일시적으로 current Environment에 새로운 값을 할당하는 일이다. 

(
var a;
a = Environment.make({
 ~a = 100;
 ~b = 200;
 ~c = 300;
});
a.postln;
)

-Environment 사용하기 

instance method “use” 는 currentEnvironment의 값을 사용하도록 한다.

(
var a;
a = Environment.make({
 ~a = 10;
 ~b = 200;
 ~c = 3000;
});
a.use({
 ~a + ~b + ~c
}).postln;
)

There is also a use class method for when you want to make and use the result from an Environment directly.

(
var a;
a = Environment.use({
 ~a = 10;
 ~b = 200;
 ~c = 3000;
 ~a + ~b + ~c
}).postln;
)

-current Environment로부터 arguments와 함께 Function불러내기

아래 예제를 보면, x, y, z를 가진 function f 를 생성하여, 그 값을 .valueEnvir(또는 valueArrayEnvir)를 통해서 지정해준다. 여기서 지정되지 않은 값은 .use에 있는 값으로 사용된다. 

(
var f;

//function
f = { arg x, y, z; [x, y, z].postln; };

Environment.use({
 ~x = 7;
 ~y = 8;
 ~z = 9;
 
 f.valueEnvir(1, 2, 3); // 모든 값이 설정됨
 f.valueEnvir(1, 2); // z 는 current Environment lookup에서
 f.valueEnvir(1); // 
 f.valueEnvir; // 
 f.valueEnvir(z: 1); // 
});
)

다음은 SynthDefs와 함께 Environment를 사용할 수 있는 예제를 보자.
아래와 같이 3개의 function들이 각각 freq, amp 와 pan 의 argument들이 서로 다른 순서로 설정되었으나, 그것과 상관없이 valueEnvir 가 environment에서 각각의 값을 불러낼 수 있다.

(
var a, b, c, n;

n = 40;
a = { arg freq, amp, pan;
 Pan2.ar(SinOsc.ar(freq), pan, amp);
};
b = { arg amp, pan, freq;
 Pan2.ar(RLPF.ar(Saw.ar(freq), freq * 6, 0.1), pan, amp);
};
c = { arg pan, freq, amp;
 Pan2.ar(Resonz.ar(GrayNoise.ar, freq * 2, 0.1), pan, amp * 2);
};

Task({
 n.do({ arg i;
  SynthDef(“Help-SPE4-EnvirDef-” ++ i.asString, {//n개 만큼의 SynthDef가 만들어 지려면 그 각각 이름에 다른 번호가 매겨지도록 사용된 것이 ++i.asString이다. 
  var out;
  Environment.use({
  //environment에 값을 지정해준다.
  ~freq = exprand(80, 600);
  ~amp = 0.1 + 0.3.rand;
  ~pan = 1.0.rand2;
   
  // 다음은 random으로 instrument function을 그 value와 함께 고르도록 한다.
  out = [a,b,c].choose.valueEnvir;
  });
  out = CombC.ar(out, 0.2, 0.2, 3, 1, out);
  out = out * EnvGen.kr( 
  Env.sine, doneAction: 2, timeScale: 1.0 + 6.0.rand, levelScale: 0.3 
  );
  Out.ar( 0, out );
  }).send(s);//서버에 보내는것을 잊지 말아야.
  0.02.wait;//task에 사용될 시간 지정
 });
 loop({
  Synth( “Help-SPE4-EnvirDef-” ++ n.rand.asString .postln);//random으로 synthdef를 뽑도록 해준다. 
  (0.5 + 2.0.rand).wait;//여기서 바로 synth를 불러준다. 
 });
}).play;
)


Leave a Comment.

This site uses Akismet to reduce spam. Learn how your comment data is processed.