package net.mkonrad.synes.synth;

import de.sciss.jcollider.Bus;
import de.sciss.jcollider.Group;
import de.sciss.jcollider.Server;
import de.sciss.jcollider.Synth;
import de.sciss.net.OSCBundle;
import de.sciss.net.OSCMessage;

public class Fader
{
  public final static int FADE_IN = 1;
  public final static int FADE_OUT = 2;
  
  private Bus _fadeOutBus;
  private Bus _fadeInBus;
  //private Server _server;
  private Group _group;
  private Synth _fadeOutSynth;
  private Synth _fadeInSynth;
  
  private String[] _argNames;
  private float[] _fadeOutValues;
  private float[] _fadeInValues;
  
  private String _synthName = "fadeCtrl";

  public Fader(Server server, Group group)
  {
    //_server = server;
    _group = group;
    _fadeOutBus = Bus.control(server);
    _fadeInBus = Bus.control(server);
    
    _argNames = new String[] { "ctrlBusIndex", "startAmp", "endAmp", "dur"};
    _fadeOutValues = new float[] { _fadeOutBus.getIndex(), 0.1f, 0.0f, 0.1f};
    _fadeInValues = new float[] { _fadeInBus.getIndex(), 0.0f, 0.1f, 0.1f};
    
    _fadeOutSynth = Synth.basicNew(_synthName, server);
    _fadeInSynth  = Synth.basicNew(_synthName, server);
  }
  

  /**
   * Creates messages to fade in or fade out a Synth (the Synth must have an
   * "amp" parameter to do so!) and adds them to an existing Bundle 
   * 
   * @param type  FADE_OUT or FADE_IN
   * @param bndl  the OSCBundle, to which the fade messages are added
   * @param synth the Synth, that shall be faded
   */
  public void addFadeMsgToBundle(int type, OSCBundle bndl, Synth synth)
  {
    Synth fadeSynth;
    float[] fadeValues;
    Bus fadeBus;
    
    if (type == FADE_OUT)
    {
      fadeSynth = _fadeOutSynth;
      fadeValues = _fadeOutValues;
      fadeBus = _fadeOutBus;
    }
    else
    {
      fadeSynth = _fadeInSynth;
      fadeValues = _fadeInValues;
      fadeBus = _fadeInBus;
    }
    
    OSCMessage fadeNewMsg = fadeSynth.addToHeadMsg(_group, _argNames, fadeValues);
    bndl.addPacket(fadeNewMsg);
    bndl.addPacket(synth.mapnMsg(new String[] { "amp" } , new Bus[] { fadeBus }));
  }
  
  /**
   * Adds messages to an existing Bundle to fade out synth1 and fade in synth2
   * 
   * @param bndl    the OSCBundle, to which the fade messages are added
   * @param synth1  the Synth to be faded out
   * @param synth2  the Synth to be faded in
   */
  public void addCrossfadeMsgToBundle(OSCBundle bndl, Synth synth1, Synth synth2)
  {
    addFadeMsgToBundle(FADE_OUT, bndl, synth1);
    addFadeMsgToBundle(FADE_IN, bndl, synth2);
  }
}
