Save This Page
Home » openjdk-7 » com.sun.media » sound » [javadoc | source]
    1   /*
    2    * Copyright (c) 2007, 2010, Oracle and/or its affiliates. All rights reserved.
    3    * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    4    *
    5    * This code is free software; you can redistribute it and/or modify it
    6    * under the terms of the GNU General Public License version 2 only, as
    7    * published by the Free Software Foundation.  Oracle designates this
    8    * particular file as subject to the "Classpath" exception as provided
    9    * by Oracle in the LICENSE file that accompanied this code.
   10    *
   11    * This code is distributed in the hope that it will be useful, but WITHOUT
   12    * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
   13    * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
   14    * version 2 for more details (a copy is included in the LICENSE file that
   15    * accompanied this code).
   16    *
   17    * You should have received a copy of the GNU General Public License version
   18    * 2 along with this work; if not, write to the Free Software Foundation,
   19    * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
   20    *
   21    * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
   22    * or visit www.oracle.com if you need additional information or have any
   23    * questions.
   24    */
   25   package com.sun.media.sound;
   26   
   27   import java.io.IOException;
   28   import java.util.Arrays;
   29   import java.util.HashMap;
   30   import java.util.Map;
   31   
   32   import javax.sound.midi.VoiceStatus;
   33   
   34   /**
   35    * Software synthesizer voice class.
   36    *
   37    * @author Karl Helgason
   38    */
   39   public class SoftVoice extends VoiceStatus {
   40   
   41       public int exclusiveClass = 0;
   42       public boolean releaseTriggered = false;
   43       private int noteOn_noteNumber = 0;
   44       private int noteOn_velocity = 0;
   45       private int noteOff_velocity = 0;
   46       private int delay = 0;
   47       protected ModelChannelMixer channelmixer = null;
   48       protected double tunedKey = 0;
   49       protected SoftTuning tuning = null;
   50       protected SoftChannel stealer_channel = null;
   51       protected ModelConnectionBlock[] stealer_extendedConnectionBlocks = null;
   52       protected SoftPerformer stealer_performer = null;
   53       protected ModelChannelMixer stealer_channelmixer = null;
   54       protected int stealer_voiceID = -1;
   55       protected int stealer_noteNumber = 0;
   56       protected int stealer_velocity = 0;
   57       protected boolean stealer_releaseTriggered = false;
   58       protected int voiceID = -1;
   59       protected boolean sustain = false;
   60       protected boolean sostenuto = false;
   61       protected boolean portamento = false;
   62       private SoftFilter filter_left;
   63       private SoftFilter filter_right;
   64       private SoftProcess eg = new SoftEnvelopeGenerator();
   65       private SoftProcess lfo = new SoftLowFrequencyOscillator();
   66       protected Map<String, SoftControl> objects =
   67               new HashMap<String, SoftControl>();
   68       protected SoftSynthesizer synthesizer;
   69       protected SoftInstrument instrument;
   70       protected SoftPerformer performer;
   71       protected SoftChannel softchannel = null;
   72       protected boolean on = false;
   73       private boolean audiostarted = false;
   74       private boolean started = false;
   75       private boolean stopping = false;
   76       private float osc_attenuation = 0.0f;
   77       private ModelOscillatorStream osc_stream;
   78       private int osc_stream_nrofchannels;
   79       private float[][] osc_buff = new float[2][];
   80       private boolean osc_stream_off_transmitted = false;
   81       private boolean out_mixer_end = false;
   82       private float out_mixer_left = 0;
   83       private float out_mixer_right = 0;
   84       private float out_mixer_effect1 = 0;
   85       private float out_mixer_effect2 = 0;
   86       private float last_out_mixer_left = 0;
   87       private float last_out_mixer_right = 0;
   88       private float last_out_mixer_effect1 = 0;
   89       private float last_out_mixer_effect2 = 0;
   90       protected ModelConnectionBlock[] extendedConnectionBlocks = null;
   91       private ModelConnectionBlock[] connections;
   92       // Last value added to destination
   93       private double[] connections_last = new double[50];
   94       // Pointer to source value
   95       private double[][][] connections_src = new double[50][3][];
   96       // Key-based override (if any)
   97       private int[][] connections_src_kc = new int[50][3];
   98       // Pointer to destination value
   99       private double[][] connections_dst = new double[50][];
  100       private boolean soundoff = false;
  101       private float lastMuteValue = 0;
  102       private float lastSoloMuteValue = 0;
  103       protected double[] co_noteon_keynumber = new double[1];
  104       protected double[] co_noteon_velocity = new double[1];
  105       protected double[] co_noteon_on = new double[1];
  106       private SoftControl co_noteon = new SoftControl() {
  107           double[] keynumber = co_noteon_keynumber;
  108           double[] velocity = co_noteon_velocity;
  109           double[] on = co_noteon_on;
  110           public double[] get(int instance, String name) {
  111               if (name == null)
  112                   return null;
  113               if (name.equals("keynumber"))
  114                   return keynumber;
  115               if (name.equals("velocity"))
  116                   return velocity;
  117               if (name.equals("on"))
  118                   return on;
  119               return null;
  120           }
  121       };
  122       private double[] co_mixer_active = new double[1];
  123       private double[] co_mixer_gain = new double[1];
  124       private double[] co_mixer_pan = new double[1];
  125       private double[] co_mixer_balance = new double[1];
  126       private double[] co_mixer_reverb = new double[1];
  127       private double[] co_mixer_chorus = new double[1];
  128       private SoftControl co_mixer = new SoftControl() {
  129           double[] active = co_mixer_active;
  130           double[] gain = co_mixer_gain;
  131           double[] pan = co_mixer_pan;
  132           double[] balance = co_mixer_balance;
  133           double[] reverb = co_mixer_reverb;
  134           double[] chorus = co_mixer_chorus;
  135           public double[] get(int instance, String name) {
  136               if (name == null)
  137                   return null;
  138               if (name.equals("active"))
  139                   return active;
  140               if (name.equals("gain"))
  141                   return gain;
  142               if (name.equals("pan"))
  143                   return pan;
  144               if (name.equals("balance"))
  145                   return balance;
  146               if (name.equals("reverb"))
  147                   return reverb;
  148               if (name.equals("chorus"))
  149                   return chorus;
  150               return null;
  151           }
  152       };
  153       private double[] co_osc_pitch = new double[1];
  154       private SoftControl co_osc = new SoftControl() {
  155           double[] pitch = co_osc_pitch;
  156           public double[] get(int instance, String name) {
  157               if (name == null)
  158                   return null;
  159               if (name.equals("pitch"))
  160                   return pitch;
  161               return null;
  162           }
  163       };
  164       private double[] co_filter_freq = new double[1];
  165       private double[] co_filter_type = new double[1];
  166       private double[] co_filter_q = new double[1];
  167       private SoftControl co_filter = new SoftControl() {
  168           double[] freq = co_filter_freq;
  169           double[] ftype = co_filter_type;
  170           double[] q = co_filter_q;
  171           public double[] get(int instance, String name) {
  172               if (name == null)
  173                   return null;
  174               if (name.equals("freq"))
  175                   return freq;
  176               if (name.equals("type"))
  177                   return ftype;
  178               if (name.equals("q"))
  179                   return q;
  180               return null;
  181           }
  182       };
  183       protected SoftResamplerStreamer resampler;
  184       private int nrofchannels;
  185   
  186       public SoftVoice(SoftSynthesizer synth) {
  187           synthesizer = synth;
  188           filter_left = new SoftFilter(synth.getFormat().getSampleRate());
  189           filter_right = new SoftFilter(synth.getFormat().getSampleRate());
  190           nrofchannels = synth.getFormat().getChannels();
  191       }
  192   
  193       private int getValueKC(ModelIdentifier id) {
  194           if (id.getObject().equals("midi_cc")) {
  195               int ic = Integer.parseInt(id.getVariable());
  196               if (ic != 0 && ic != 32) {
  197                   if (ic < 120)
  198                       return ic;
  199               }
  200           } else if (id.getObject().equals("midi_rpn")) {
  201               if (id.getVariable().equals("1"))
  202                   return 120; // Fine tuning
  203               if (id.getVariable().equals("2"))
  204                   return 121; // Coarse tuning
  205           }
  206           return -1;
  207       }
  208   
  209       private double[] getValue(ModelIdentifier id) {
  210           SoftControl o = objects.get(id.getObject());
  211           if (o == null)
  212               return null;
  213           return o.get(id.getInstance(), id.getVariable());
  214       }
  215   
  216       private double transformValue(double value, ModelSource src) {
  217           if (src.getTransform() != null)
  218               return src.getTransform().transform(value);
  219           else
  220               return value;
  221       }
  222   
  223       private double transformValue(double value, ModelDestination dst) {
  224           if (dst.getTransform() != null)
  225               return dst.getTransform().transform(value);
  226           else
  227               return value;
  228       }
  229   
  230       private double processKeyBasedController(double value, int keycontrol) {
  231           if (keycontrol == -1)
  232               return value;
  233           if (softchannel.keybasedcontroller_active != null)
  234               if (softchannel.keybasedcontroller_active[note] != null)
  235                   if (softchannel.keybasedcontroller_active[note][keycontrol]) {
  236                       double key_controlvalue =
  237                               softchannel.keybasedcontroller_value[note][keycontrol];
  238                       if (keycontrol == 10 || keycontrol == 91 || keycontrol == 93)
  239                           return key_controlvalue;
  240                       value += key_controlvalue * 2.0 - 1.0;
  241                       if (value > 1)
  242                           value = 1;
  243                       else if (value < 0)
  244                           value = 0;
  245                   }
  246           return value;
  247       }
  248   
  249       private void processConnection(int ix) {
  250           ModelConnectionBlock conn = connections[ix];
  251           double[][] src = connections_src[ix];
  252           double[] dst = connections_dst[ix];
  253           if (dst == null || Double.isInfinite(dst[0]))
  254               return;
  255   
  256           double value = conn.getScale();
  257           if (softchannel.keybasedcontroller_active == null) {
  258               ModelSource[] srcs = conn.getSources();
  259               for (int i = 0; i < srcs.length; i++) {
  260                   value *= transformValue(src[i][0], srcs[i]);
  261                   if (value == 0)
  262                       break;
  263               }
  264           } else {
  265               ModelSource[] srcs = conn.getSources();
  266               int[] src_kc = connections_src_kc[ix];
  267               for (int i = 0; i < srcs.length; i++) {
  268                   value *= transformValue(processKeyBasedController(src[i][0],
  269                           src_kc[i]), srcs[i]);
  270                   if (value == 0)
  271                       break;
  272               }
  273           }
  274   
  275           value = transformValue(value, conn.getDestination());
  276           dst[0] = dst[0] - connections_last[ix] + value;
  277           connections_last[ix] = value;
  278           // co_mixer_gain[0] = 0;
  279       }
  280   
  281       protected void updateTuning(SoftTuning newtuning) {
  282           tuning = newtuning;
  283           tunedKey = tuning.getTuning(note) / 100.0;
  284           if (!portamento) {
  285               co_noteon_keynumber[0] = tunedKey * (1.0 / 128.0);
  286               if(performer == null)
  287                   return;
  288               int[] c = performer.midi_connections[4];
  289               if (c == null)
  290                   return;
  291               for (int i = 0; i < c.length; i++)
  292                   processConnection(c[i]);
  293           }
  294       }
  295   
  296       protected void setNote(int noteNumber) {
  297           note = noteNumber;
  298           tunedKey = tuning.getTuning(noteNumber) / 100.0;
  299       }
  300   
  301       protected void noteOn(int noteNumber, int velocity, int delay) {
  302   
  303           sustain = false;
  304           sostenuto = false;
  305           portamento = false;
  306   
  307           soundoff = false;
  308           on = true;
  309           active = true;
  310           started = true;
  311           // volume = velocity;
  312   
  313           noteOn_noteNumber = noteNumber;
  314           noteOn_velocity = velocity;
  315           this.delay = delay;
  316   
  317           lastMuteValue = 0;
  318           lastSoloMuteValue = 0;
  319   
  320           setNote(noteNumber);
  321   
  322           if (performer.forcedKeynumber)
  323               co_noteon_keynumber[0] = 0;
  324           else
  325               co_noteon_keynumber[0] = tunedKey * (1f / 128f);
  326           if (performer.forcedVelocity)
  327               co_noteon_velocity[0] = 0;
  328           else
  329               co_noteon_velocity[0] = velocity * (1f / 128f);
  330           co_mixer_active[0] = 0;
  331           co_mixer_gain[0] = 0;
  332           co_mixer_pan[0] = 0;
  333           co_mixer_balance[0] = 0;
  334           co_mixer_reverb[0] = 0;
  335           co_mixer_chorus[0] = 0;
  336           co_osc_pitch[0] = 0;
  337           co_filter_freq[0] = 0;
  338           co_filter_q[0] = 0;
  339           co_filter_type[0] = 0;
  340           co_noteon_on[0] = 1;
  341   
  342           eg.reset();
  343           lfo.reset();
  344           filter_left.reset();
  345           filter_right.reset();
  346   
  347           objects.put("master", synthesizer.getMainMixer().co_master);
  348           objects.put("eg", eg);
  349           objects.put("lfo", lfo);
  350           objects.put("noteon", co_noteon);
  351           objects.put("osc", co_osc);
  352           objects.put("mixer", co_mixer);
  353           objects.put("filter", co_filter);
  354   
  355           connections = performer.connections;
  356   
  357           if (connections_last == null
  358                   || connections_last.length < connections.length) {
  359               connections_last = new double[connections.length];
  360           }
  361           if (connections_src == null
  362                   || connections_src.length < connections.length) {
  363               connections_src = new double[connections.length][][];
  364               connections_src_kc = new int[connections.length][];
  365           }
  366           if (connections_dst == null
  367                   || connections_dst.length < connections.length) {
  368               connections_dst = new double[connections.length][];
  369           }
  370           for (int i = 0; i < connections.length; i++) {
  371               ModelConnectionBlock conn = connections[i];
  372               connections_last[i] = 0;
  373               if (conn.getSources() != null) {
  374                   ModelSource[] srcs = conn.getSources();
  375                   if (connections_src[i] == null
  376                           || connections_src[i].length < srcs.length) {
  377                       connections_src[i] = new double[srcs.length][];
  378                       connections_src_kc[i] = new int[srcs.length];
  379                   }
  380                   double[][] src = connections_src[i];
  381                   int[] src_kc = connections_src_kc[i];
  382                   connections_src[i] = src;
  383                   for (int j = 0; j < srcs.length; j++) {
  384                       src_kc[j] = getValueKC(srcs[j].getIdentifier());
  385                       src[j] = getValue(srcs[j].getIdentifier());
  386                   }
  387               }
  388   
  389               if (conn.getDestination() != null)
  390                   connections_dst[i] = getValue(conn.getDestination()
  391                           .getIdentifier());
  392               else
  393                   connections_dst[i] = null;
  394           }
  395   
  396           for (int i = 0; i < connections.length; i++)
  397               processConnection(i);
  398   
  399           if (extendedConnectionBlocks != null) {
  400               for (ModelConnectionBlock connection: extendedConnectionBlocks) {
  401                   double value = 0;
  402   
  403                   if (softchannel.keybasedcontroller_active == null) {
  404                       for (ModelSource src: connection.getSources()) {
  405                           double x = getValue(src.getIdentifier())[0];
  406                           ModelTransform t = src.getTransform();
  407                           if (t == null)
  408                               value += x;
  409                           else
  410                               value += t.transform(x);
  411                       }
  412                   } else {
  413                       for (ModelSource src: connection.getSources()) {
  414                           double x = getValue(src.getIdentifier())[0];
  415                           x = processKeyBasedController(x,
  416                                   getValueKC(src.getIdentifier()));
  417                           ModelTransform t = src.getTransform();
  418                           if (t == null)
  419                               value += x;
  420                           else
  421                               value += t.transform(x);
  422                       }
  423                   }
  424   
  425                   ModelDestination dest = connection.getDestination();
  426                   ModelTransform t = dest.getTransform();
  427                   if (t != null)
  428                       value = t.transform(value);
  429                   getValue(dest.getIdentifier())[0] += value;
  430               }
  431           }
  432   
  433           eg.init(synthesizer);
  434           lfo.init(synthesizer);
  435   
  436       }
  437   
  438       protected void setPolyPressure(int pressure) {
  439           if(performer == null)
  440               return;
  441           int[] c = performer.midi_connections[2];
  442           if (c == null)
  443               return;
  444           for (int i = 0; i < c.length; i++)
  445               processConnection(c[i]);
  446       }
  447   
  448       protected void setChannelPressure(int pressure) {
  449           if(performer == null)
  450               return;
  451           int[] c = performer.midi_connections[1];
  452           if (c == null)
  453               return;
  454           for (int i = 0; i < c.length; i++)
  455               processConnection(c[i]);
  456       }
  457   
  458       protected void controlChange(int controller, int value) {
  459           if(performer == null)
  460               return;
  461           int[] c = performer.midi_ctrl_connections[controller];
  462           if (c == null)
  463               return;
  464           for (int i = 0; i < c.length; i++)
  465               processConnection(c[i]);
  466       }
  467   
  468       protected void nrpnChange(int controller, int value) {
  469           if(performer == null)
  470               return;
  471           int[] c = performer.midi_nrpn_connections.get(controller);
  472           if (c == null)
  473               return;
  474           for (int i = 0; i < c.length; i++)
  475               processConnection(c[i]);
  476       }
  477   
  478       protected void rpnChange(int controller, int value) {
  479           if(performer == null)
  480               return;
  481           int[] c = performer.midi_rpn_connections.get(controller);
  482           if (c == null)
  483               return;
  484           for (int i = 0; i < c.length; i++)
  485               processConnection(c[i]);
  486       }
  487   
  488       protected void setPitchBend(int bend) {
  489           if(performer == null)
  490               return;
  491           int[] c = performer.midi_connections[0];
  492           if (c == null)
  493               return;
  494           for (int i = 0; i < c.length; i++)
  495               processConnection(c[i]);
  496       }
  497   
  498       protected void setMute(boolean mute) {
  499           co_mixer_gain[0] -= lastMuteValue;
  500           lastMuteValue = mute ? -960 : 0;
  501           co_mixer_gain[0] += lastMuteValue;
  502       }
  503   
  504       protected void setSoloMute(boolean mute) {
  505           co_mixer_gain[0] -= lastSoloMuteValue;
  506           lastSoloMuteValue = mute ? -960 : 0;
  507           co_mixer_gain[0] += lastSoloMuteValue;
  508       }
  509   
  510       protected void shutdown() {
  511           if (co_noteon_on[0] < -0.5)
  512               return;
  513           on = false;
  514   
  515           co_noteon_on[0] = -1;
  516   
  517           if(performer == null)
  518               return;
  519           int[] c = performer.midi_connections[3];
  520           if (c == null)
  521               return;
  522           for (int i = 0; i < c.length; i++)
  523               processConnection(c[i]);
  524       }
  525   
  526       protected void soundOff() {
  527           on = false;
  528           soundoff = true;
  529       }
  530   
  531       protected void noteOff(int velocity) {
  532           if (!on)
  533               return;
  534           on = false;
  535   
  536           noteOff_velocity = velocity;
  537   
  538           if (softchannel.sustain) {
  539               sustain = true;
  540               return;
  541           }
  542           if (sostenuto)
  543               return;
  544   
  545           co_noteon_on[0] = 0;
  546   
  547           if(performer == null)
  548               return;
  549           int[] c = performer.midi_connections[3];
  550           if (c == null)
  551               return;
  552           for (int i = 0; i < c.length; i++)
  553               processConnection(c[i]);
  554       }
  555   
  556       protected void redamp() {
  557           if (co_noteon_on[0] > 0.5)
  558               return;
  559           if (co_noteon_on[0] < -0.5)
  560               return; // don't redamp notes in shutdown stage
  561   
  562           sustain = true;
  563           co_noteon_on[0] = 1;
  564   
  565           if(performer == null)
  566               return;
  567           int[] c = performer.midi_connections[3];
  568           if (c == null)
  569               return;
  570           for (int i = 0; i < c.length; i++)
  571               processConnection(c[i]);
  572       }
  573   
  574       protected void processControlLogic() {
  575           if (stopping) {
  576               active = false;
  577               stopping = false;
  578               audiostarted = false;
  579               instrument = null;
  580               performer = null;
  581               connections = null;
  582               extendedConnectionBlocks = null;
  583               channelmixer = null;
  584               if (osc_stream != null)
  585                   try {
  586                       osc_stream.close();
  587                   } catch (IOException e) {
  588                       //e.printStackTrace();
  589                   }
  590   
  591               if (stealer_channel != null) {
  592                   stealer_channel.initVoice(this, stealer_performer,
  593                           stealer_voiceID, stealer_noteNumber, stealer_velocity, 0,
  594                           stealer_extendedConnectionBlocks, stealer_channelmixer,
  595                           stealer_releaseTriggered);
  596                   stealer_releaseTriggered = false;
  597                   stealer_channel = null;
  598                   stealer_performer = null;
  599                   stealer_voiceID = -1;
  600                   stealer_noteNumber = 0;
  601                   stealer_velocity = 0;
  602                   stealer_extendedConnectionBlocks = null;
  603                   stealer_channelmixer = null;
  604               }
  605           }
  606           if (started) {
  607               audiostarted = true;
  608   
  609               ModelOscillator osc = performer.oscillators[0];
  610   
  611               osc_stream_off_transmitted = false;
  612               if (osc instanceof ModelWavetable) {
  613                   try {
  614                       resampler.open((ModelWavetable)osc,
  615                               synthesizer.getFormat().getSampleRate());
  616                       osc_stream = resampler;
  617                   } catch (IOException e) {
  618                       //e.printStackTrace();
  619                   }
  620               } else {
  621                   osc_stream = osc.open(synthesizer.getFormat().getSampleRate());
  622               }
  623               osc_attenuation = osc.getAttenuation();
  624               osc_stream_nrofchannels = osc.getChannels();
  625               if (osc_buff == null || osc_buff.length < osc_stream_nrofchannels)
  626                   osc_buff = new float[osc_stream_nrofchannels][];
  627   
  628               if (osc_stream != null)
  629                   osc_stream.noteOn(softchannel, this, noteOn_noteNumber,
  630                           noteOn_velocity);
  631   
  632   
  633           }
  634           if (audiostarted) {
  635               if (portamento) {
  636                   double note_delta = tunedKey - (co_noteon_keynumber[0] * 128);
  637                   double note_delta_a = Math.abs(note_delta);
  638                   if (note_delta_a < 0.0000000001) {
  639                       co_noteon_keynumber[0] = tunedKey * (1.0 / 128.0);
  640                       portamento = false;
  641                   } else {
  642                       if (note_delta_a > softchannel.portamento_time)
  643                           note_delta = Math.signum(note_delta)
  644                                   * softchannel.portamento_time;
  645                       co_noteon_keynumber[0] += note_delta * (1.0 / 128.0);
  646                   }
  647   
  648                   int[] c = performer.midi_connections[4];
  649                   if (c == null)
  650                       return;
  651                   for (int i = 0; i < c.length; i++)
  652                       processConnection(c[i]);
  653               }
  654   
  655               eg.processControlLogic();
  656               lfo.processControlLogic();
  657   
  658               for (int i = 0; i < performer.ctrl_connections.length; i++)
  659                   processConnection(performer.ctrl_connections[i]);
  660   
  661               osc_stream.setPitch((float)co_osc_pitch[0]);
  662   
  663               int filter_type = (int)co_filter_type[0];
  664               double filter_freq;
  665   
  666               if (co_filter_freq[0] == 13500.0)
  667                   filter_freq = 19912.126958213175;
  668               else
  669                   filter_freq = 440.0 * Math.exp(
  670                           ((co_filter_freq[0]) - 6900.0) *
  671                           (Math.log(2.0) / 1200.0));
  672               /*
  673               filter_freq = 440.0 * Math.pow(2.0,
  674               ((co_filter_freq[0]) - 6900.0) / 1200.0);*/
  675               /*
  676                * double velocity = co_noteon_velocity[0]; if(velocity < 0.5)
  677                * filter_freq *= ((velocity * 2)*0.75 + 0.25);
  678                */
  679   
  680               double q = co_filter_q[0] / 10.0;
  681               filter_left.setFilterType(filter_type);
  682               filter_left.setFrequency(filter_freq);
  683               filter_left.setResonance(q);
  684               filter_right.setFilterType(filter_type);
  685               filter_right.setFrequency(filter_freq);
  686               filter_right.setResonance(q);
  687               /*
  688               float gain = (float) Math.pow(10,
  689               (-osc_attenuation + co_mixer_gain[0]) / 200.0);
  690                */
  691               float gain = (float)Math.exp(
  692                       (-osc_attenuation + co_mixer_gain[0])*(Math.log(10) / 200.0));
  693   
  694               if (co_mixer_gain[0] <= -960)
  695                   gain = 0;
  696   
  697               if (soundoff) {
  698                   stopping = true;
  699                   gain = 0;
  700                   /*
  701                    * if(co_mixer_gain[0] > -960)
  702                    *   co_mixer_gain[0] -= 960;
  703                    */
  704               }
  705   
  706               volume = (int)(Math.sqrt(gain) * 128);
  707   
  708               // gain *= 0.2;
  709   
  710               double pan = co_mixer_pan[0] * (1.0 / 1000.0);
  711               // System.out.println("pan = " + pan);
  712               if (pan < 0)
  713                   pan = 0;
  714               else if (pan > 1)
  715                   pan = 1;
  716   
  717               if (pan == 0.5) {
  718                   out_mixer_left = gain * 0.7071067811865476f;
  719                   out_mixer_right = out_mixer_left;
  720               } else {
  721                   out_mixer_left = gain * (float)Math.cos(pan * Math.PI * 0.5);
  722                   out_mixer_right = gain * (float)Math.sin(pan * Math.PI * 0.5);
  723               }
  724   
  725               double balance = co_mixer_balance[0] * (1.0 / 1000.0);
  726               if (balance != 0.5) {
  727                   if (balance > 0.5)
  728                       out_mixer_left *= (1 - balance) * 2;
  729                   else
  730                       out_mixer_right *= balance * 2;
  731               }
  732   
  733               if (synthesizer.reverb_on) {
  734                   out_mixer_effect1 = (float)(co_mixer_reverb[0] * (1.0 / 1000.0));
  735                   out_mixer_effect1 *= gain;
  736               } else
  737                   out_mixer_effect1 = 0;
  738               if (synthesizer.chorus_on) {
  739                   out_mixer_effect2 = (float)(co_mixer_chorus[0] * (1.0 / 1000.0));
  740                   out_mixer_effect2 *= gain;
  741               } else
  742                   out_mixer_effect2 = 0;
  743               out_mixer_end = co_mixer_active[0] < 0.5;
  744   
  745               if (!on)
  746                   if (!osc_stream_off_transmitted) {
  747                       osc_stream_off_transmitted = true;
  748                       if (osc_stream != null)
  749                           osc_stream.noteOff(noteOff_velocity);
  750                   }
  751   
  752           }
  753           if (started) {
  754               last_out_mixer_left = out_mixer_left;
  755               last_out_mixer_right = out_mixer_right;
  756               last_out_mixer_effect1 = out_mixer_effect1;
  757               last_out_mixer_effect2 = out_mixer_effect2;
  758               started = false;
  759           }
  760   
  761       }
  762   
  763       protected void mixAudioStream(SoftAudioBuffer in, SoftAudioBuffer out,
  764               SoftAudioBuffer dout,
  765               float amp_from, float amp_to) {
  766           int bufferlen = in.getSize();
  767           if (amp_from < 0.000000001 && amp_to < 0.000000001)
  768               return;
  769           if(dout != null && delay != 0)
  770           {
  771               if (amp_from == amp_to) {
  772                   float[] fout = out.array();
  773                   float[] fin = in.array();
  774                   int j = 0;
  775                   for (int i = delay; i < bufferlen; i++)
  776                       fout[i] += fin[j++] * amp_to;
  777                   fout = dout.array();
  778                   for (int i = 0; i < delay; i++)
  779                       fout[i] += fin[j++] * amp_to;
  780               } else {
  781                   float amp = amp_from;
  782                   float amp_delta = (amp_to - amp_from) / bufferlen;
  783                   float[] fout = out.array();
  784                   float[] fin = in.array();
  785                   int j = 0;
  786                   for (int i = delay; i < bufferlen; i++) {
  787                       amp += amp_delta;
  788                       fout[i] += fin[j++] * amp;
  789                   }
  790                   fout = dout.array();
  791                   for (int i = 0; i < delay; i++) {
  792                       amp += amp_delta;
  793                       fout[i] += fin[j++] * amp;
  794                   }
  795               }
  796           }
  797           else
  798           {
  799               if (amp_from == amp_to) {
  800                   float[] fout = out.array();
  801                   float[] fin = in.array();
  802                   for (int i = 0; i < bufferlen; i++)
  803                       fout[i] += fin[i] * amp_to;
  804               } else {
  805                   float amp = amp_from;
  806                   float amp_delta = (amp_to - amp_from) / bufferlen;
  807                   float[] fout = out.array();
  808                   float[] fin = in.array();
  809                   for (int i = 0; i < bufferlen; i++) {
  810                       amp += amp_delta;
  811                       fout[i] += fin[i] * amp;
  812                   }
  813               }
  814           }
  815   
  816       }
  817   
  818       protected void processAudioLogic(SoftAudioBuffer[] buffer) {
  819           if (!audiostarted)
  820               return;
  821   
  822           int bufferlen = buffer[0].getSize();
  823   
  824           try {
  825               osc_buff[0] = buffer[SoftMainMixer.CHANNEL_LEFT_DRY].array();
  826               if (nrofchannels != 1)
  827                   osc_buff[1] = buffer[SoftMainMixer.CHANNEL_RIGHT_DRY].array();
  828               int ret = osc_stream.read(osc_buff, 0, bufferlen);
  829               if (ret == -1) {
  830                   stopping = true;
  831                   return;
  832               }
  833               if (ret != bufferlen) {
  834                   Arrays.fill(osc_buff[0], ret, bufferlen, 0f);
  835                   if (nrofchannels != 1)
  836                       Arrays.fill(osc_buff[1], ret, bufferlen, 0f);
  837               }
  838   
  839           } catch (IOException e) {
  840               //e.printStackTrace();
  841           }
  842   
  843           SoftAudioBuffer left = buffer[SoftMainMixer.CHANNEL_LEFT];
  844           SoftAudioBuffer right = buffer[SoftMainMixer.CHANNEL_RIGHT];
  845           SoftAudioBuffer mono = buffer[SoftMainMixer.CHANNEL_MONO];
  846           SoftAudioBuffer eff1 = buffer[SoftMainMixer.CHANNEL_EFFECT1];
  847           SoftAudioBuffer eff2 = buffer[SoftMainMixer.CHANNEL_EFFECT2];
  848   
  849           SoftAudioBuffer dleft = buffer[SoftMainMixer.CHANNEL_DELAY_LEFT];
  850           SoftAudioBuffer dright = buffer[SoftMainMixer.CHANNEL_DELAY_RIGHT];
  851           SoftAudioBuffer dmono = buffer[SoftMainMixer.CHANNEL_DELAY_MONO];
  852           SoftAudioBuffer deff1 = buffer[SoftMainMixer.CHANNEL_DELAY_EFFECT1];
  853           SoftAudioBuffer deff2 = buffer[SoftMainMixer.CHANNEL_DELAY_EFFECT2];
  854   
  855           SoftAudioBuffer leftdry = buffer[SoftMainMixer.CHANNEL_LEFT_DRY];
  856           SoftAudioBuffer rightdry = buffer[SoftMainMixer.CHANNEL_RIGHT_DRY];
  857   
  858           if (osc_stream_nrofchannels == 1)
  859               rightdry = null;
  860   
  861           if (!Double.isInfinite(co_filter_freq[0])) {
  862               filter_left.processAudio(leftdry);
  863               if (rightdry != null)
  864                   filter_right.processAudio(rightdry);
  865           }
  866   
  867           if (nrofchannels == 1) {
  868               out_mixer_left = (out_mixer_left + out_mixer_right) / 2;
  869               mixAudioStream(leftdry, left, dleft, last_out_mixer_left, out_mixer_left);
  870               if (rightdry != null)
  871                   mixAudioStream(rightdry, left, dleft, last_out_mixer_left,
  872                           out_mixer_left);
  873           } else {
  874               if(rightdry == null &&
  875                       last_out_mixer_left == last_out_mixer_right &&
  876                       out_mixer_left == out_mixer_right)
  877               {
  878                   mixAudioStream(leftdry, mono, dmono, last_out_mixer_left, out_mixer_left);
  879               }
  880               else
  881               {
  882                   mixAudioStream(leftdry, left, dleft, last_out_mixer_left, out_mixer_left);
  883                   if (rightdry != null)
  884                       mixAudioStream(rightdry, right, dright, last_out_mixer_right,
  885                           out_mixer_right);
  886                   else
  887                       mixAudioStream(leftdry, right, dright, last_out_mixer_right,
  888                           out_mixer_right);
  889               }
  890           }
  891   
  892           if (rightdry == null) {
  893               mixAudioStream(leftdry, eff1, deff1, last_out_mixer_effect1,
  894                       out_mixer_effect1);
  895               mixAudioStream(leftdry, eff2, deff2, last_out_mixer_effect2,
  896                       out_mixer_effect2);
  897           } else {
  898               mixAudioStream(leftdry, eff1, deff1, last_out_mixer_effect1 * 0.5f,
  899                       out_mixer_effect1 * 0.5f);
  900               mixAudioStream(leftdry, eff2, deff2, last_out_mixer_effect2 * 0.5f,
  901                       out_mixer_effect2 * 0.5f);
  902               mixAudioStream(rightdry, eff1, deff1, last_out_mixer_effect1 * 0.5f,
  903                       out_mixer_effect1 * 0.5f);
  904               mixAudioStream(rightdry, eff2, deff2, last_out_mixer_effect2 * 0.5f,
  905                       out_mixer_effect2 * 0.5f);
  906           }
  907   
  908           last_out_mixer_left = out_mixer_left;
  909           last_out_mixer_right = out_mixer_right;
  910           last_out_mixer_effect1 = out_mixer_effect1;
  911           last_out_mixer_effect2 = out_mixer_effect2;
  912   
  913           if (out_mixer_end) {
  914               stopping = true;
  915           }
  916   
  917       }
  918   }

Save This Page
Home » openjdk-7 » com.sun.media » sound » [javadoc | source]