/[svn]/linuxsampler/trunk/src/engines/common/SignalUnit.h
ViewVC logotype

Diff of /linuxsampler/trunk/src/engines/common/SignalUnit.h

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 2217 by iliev, Tue Jul 26 15:51:30 2011 UTC revision 2227 by iliev, Wed Aug 3 17:11:40 2011 UTC
# Line 28  Line 28 
28    
29  namespace LinuxSampler {  namespace LinuxSampler {
30    
31        template<typename T>
32        class FixedArray {
33            public:
34                FixedArray(int capacity) {
35                    iSize = 0;
36                    iCapacity = capacity;
37                    pData = new T[iCapacity];
38                }
39                
40                ~FixedArray() {
41                    delete pData;
42                    pData = NULL;
43                }
44                
45                inline int size() const { return iSize; }
46                inline int capacity() { return iCapacity; }
47                
48                void add(T element) {
49                    if (iSize >= iCapacity) throw Exception("Array out of bounds");
50                    pData[iSize++] = element;
51                }
52                
53                
54                T increment() {
55                    if (iSize >= iCapacity) throw Exception("Array out of bounds");
56                    return pData[iSize++];
57                }
58                
59                void clear() { iSize = 0; }
60                
61                void copy(const FixedArray<T>& array) {
62                    if(array.size() >= capacity()) throw Exception("Not enough space to copy array");
63                    for (int i = 0; i < array.size(); i++) pData[i] = array[i];
64                    iSize = array.size();
65                }
66                
67                inline T& operator[](int idx) const {
68                    return pData[idx];
69                }
70                
71            private:
72                T*   pData;
73                int  iSize;
74                int  iCapacity;
75        };
76        
77      class SignalUnitRack;      class SignalUnitRack;
78    
79      /**      /**
# Line 83  namespace LinuxSampler { Line 129  namespace LinuxSampler {
129                  Parameter(const Parameter& Prm) { Copy(Prm); }                  Parameter(const Parameter& Prm) { Copy(Prm); }
130                  void operator=(const Parameter& Prm) { Copy(Prm); }                  void operator=(const Parameter& Prm) { Copy(Prm); }
131                            
132                  virtual void Copy(const Parameter& Prm) {                  void Copy(const Parameter& Prm) {
133                      if (this == &Prm) return;                      if (this == &Prm) return;
134    
135                      pUnit = Prm.pUnit;                      pUnit = Prm.pUnit;
# Line 121  namespace LinuxSampler { Line 167  namespace LinuxSampler {
167              SignalUnit(const SignalUnit& Unit): pRack(Unit.pRack) { Copy(Unit); }              SignalUnit(const SignalUnit& Unit): pRack(Unit.pRack) { Copy(Unit); }
168              void operator=(const SignalUnit& Unit) { Copy(Unit); }              void operator=(const SignalUnit& Unit) { Copy(Unit); }
169                            
170              virtual void Copy(const SignalUnit& Unit) {              void Copy(const SignalUnit& Unit) {
171                  if (this == &Unit) return;                  if (this == &Unit) return;
172    
173                  bActive = Unit.bActive;                  bActive = Unit.bActive;
# Line 251  namespace LinuxSampler { Line 297  namespace LinuxSampler {
297               */               */
298              virtual float GetResonance() = 0;              virtual float GetResonance() = 0;
299                            
300                /** Should return value in the range [-100, 100] (L <-> R) */
301                virtual float GetPan() = 0;
302                
303              virtual float CalculateFilterCutoff(float cutoff) {              virtual float CalculateFilterCutoff(float cutoff) {
304                  cutoff *= GetFilterCutoff();                  cutoff *= GetFilterCutoff();
305                  return cutoff > 13500 ? 13500 : cutoff;                  return cutoff > 13500 ? 13500 : cutoff;
# Line 263  namespace LinuxSampler { Line 312  namespace LinuxSampler {
312              virtual float CalculateResonance(float res) {              virtual float CalculateResonance(float res) {
313                  return GetResonance() * res;                  return GetResonance() * res;
314              }              }
315                
316                /** Should return value in the range [0, 127] (L <-> R) */
317                virtual uint8_t CaluclatePan(uint8_t pan) {
318                    int p = pan + GetPan() * 0.63;
319                    if (p < 0) return 0;
320                    if (p > 127) return 127;
321                    return p;
322                }
323      };      };
324            
325      /**      /**
326       * Continuous controller signal unit.       * Continuous controller signal unit.
327       * The level of this unit corresponds to the controller changes       * The level of this unit corresponds to the controllers changes
328       * and is normalized to be in the range from -1 to +1.       * and their influences.
329       */       */
330      class CCSignalUnit: public SignalUnit {      class CCSignalUnit: public SignalUnit {
331          private:          public:
332              uint8_t Ctrl; // The number of the MIDI controller which modulates this signal unit.              /** Listener which will be notified when the level of the unit is changed. */
333                class Listener {
334                    public:
335                        virtual void ValueChanged(CCSignalUnit* pUnit) = 0;
336                };
337                
338            protected:
339                class CC {
340                    public:
341                        uint8_t Controller;  ///< MIDI controller number.
342                        uint8_t Value;       ///< Controller Value.
343                        float   Influence;
344                        
345                        CC() {
346                            CC(0, 0.0f);
347                        }
348                        
349                        CC(uint8_t Controller, float Influence) {
350                            this->Controller = Controller;
351                            this->Value = 0;
352                            this->Influence = Influence;
353                        }
354                        
355                        CC(const CC& cc) { Copy(cc); }
356                        void operator=(const CC& cc) { Copy(cc); }
357                        
358                        void Copy(const CC& cc) {
359                            Controller = cc.Controller;
360                            Value = cc.Value;
361                            Influence = cc.Influence;
362                        }
363                };
364                
365                FixedArray<CC> Ctrls; // The MIDI controllers which modulates this signal unit.
366                Listener* pListener;
367    
368          public:          public:
369              CCSignalUnit(SignalUnitRack* rack, uint8_t Controller): SignalUnit(rack) {              
370                  Ctrl = Controller;              CCSignalUnit(SignalUnitRack* rack, Listener* l = NULL): SignalUnit(rack), Ctrls(128) {
371                    pListener = l;
372              }              }
373                            
374              CCSignalUnit(const CCSignalUnit& Unit): SignalUnit(Unit) { Copy(Unit); }              CCSignalUnit(const CCSignalUnit& Unit): SignalUnit(Unit.pRack), Ctrls(128) { Copy(Unit); }
375              void operator=(const CCSignalUnit& Unit) { SignalUnit::Copy(Unit); Copy(Unit); }              void operator=(const CCSignalUnit& Unit) { Copy(Unit); }
376                
377                void Copy(const CCSignalUnit& Unit) {
378                    Ctrls.copy(Unit.Ctrls);
379                    pListener = Unit.pListener;
380                    SignalUnit::Copy(Unit);
381                }
382                            
383              virtual void Copy(const CCSignalUnit& Unit) {              void AddCC(uint8_t Controller, float Influence) {
384                  Ctrl = Unit.Ctrl;                  Ctrls.add(CC(Controller, Influence));
385                }
386                
387                void RemoveAllCCs() {
388                    Ctrls.clear();
389              }              }
390                            
391              virtual void Increment() { }              virtual void Increment() { }
392                            
393                virtual void Trigger() {
394                    Calculate();
395                    bActive = Level != 0;
396                }
397                
398              virtual void ProcessCCEvent(uint8_t Controller, uint8_t Value) {              virtual void ProcessCCEvent(uint8_t Controller, uint8_t Value) {
399                  if (Controller != Ctrl) return;                  bool recalculate = false;
400                                    
401                  // Normalize the value so it belongs to the interval [-1, +1]                  for (int i = 0; i < Ctrls.size(); i++) {
402                  Level = 2 * Value;                      if (Controller != Ctrls[i].Controller) continue;
403                  Level = Level/127.0f - 1.0f;                      if (Ctrls[i].Value == Value) continue;
404                        Ctrls[i].Value = Value;
405                        if (!bActive) bActive = true;
406                        recalculate = true;
407                    }
408                                    
409                  if (!bActive) bActive = true;                  if (recalculate) {
410                        Calculate();
411                        if (pListener!= NULL) pListener->ValueChanged(this);
412                    }
413                }
414                
415                virtual void Calculate() {
416                    Level = 0;
417                    for (int i = 0; i < Ctrls.size(); i++) {
418                        if (Ctrls[i].Value == 0) continue;
419                        Level += (Ctrls[i].Value / 127.0f) * Ctrls[i].Influence;
420                    }
421              }              }
422      };      };
423            

Legend:
Removed from v.2217  
changed lines
  Added in v.2227

  ViewVC Help
Powered by ViewVC