You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

141 lines
4.1KB

  1. /* SpiralSound
  2. * Copyleft (C) 2002 Andy Preston <andy@clubunix.co.uk>
  3. *
  4. * This program is free software; you can redistribute it and/or modify
  5. * it under the terms of the GNU General Public License as published by
  6. * the Free Software Foundation; either version 2 of the License, or
  7. * (at your option) any later version.
  8. *
  9. * This program is distributed in the hope that it will be useful,
  10. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  11. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  12. * GNU General Public License for more details.
  13. *
  14. * You should have received a copy of the GNU General Public License
  15. * along with this program; if not, write to the Free Software
  16. * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
  17. */
  18. #include "LFOPlugin.h"
  19. #include "LFOPluginGUI.h"
  20. #include <Fl/Fl_Button.H>
  21. #include "SpiralIcon.xpm"
  22. using namespace std;
  23. extern "C" {
  24. SpiralPlugin* SpiralPlugin_CreateInstance() { return new LFOPlugin; }
  25. char** SpiralPlugin_GetIcon() { return SpiralIcon_xpm; }
  26. int SpiralPlugin_GetID() { return 124; }
  27. string SpiralPlugin_GetGroupName() { return "Oscillators"; }
  28. }
  29. ///////////////////////////////////////////////////////
  30. LFOPlugin::LFOPlugin() :
  31. m_Type (SINE),
  32. m_Freq (0.1),
  33. m_TableLength (DEFAULT_TABLE_LEN) {
  34. m_CyclePos = 0;
  35. m_Note = 0;
  36. m_PluginInfo.Name = "LFO";
  37. m_PluginInfo.Width = 180;
  38. m_PluginInfo.Height = 100;
  39. m_PluginInfo.NumInputs = 0;
  40. m_PluginInfo.NumOutputs = 3;
  41. m_PluginInfo.PortTips.push_back ("Output");
  42. m_PluginInfo.PortTips.push_back ("'Cosine' Output");
  43. m_PluginInfo.PortTips.push_back ("Inverted Output");
  44. m_AudioCH->Register("Freq", &m_Freq);
  45. m_AudioCH->Register("Type", (char*)&m_Type);
  46. }
  47. LFOPlugin::~LFOPlugin() {
  48. }
  49. PluginInfo &LFOPlugin::Initialise (const HostInfo *Host) {
  50. PluginInfo& Info= SpiralPlugin::Initialise (Host);
  51. for (int n=0; n<NUM_TABLES; n++)
  52. m_Table[n].Allocate (m_TableLength);
  53. WriteWaves();
  54. return Info;
  55. }
  56. SpiralGUIType *LFOPlugin::CreateGUI() {
  57. return new LFOPluginGUI(m_PluginInfo.Width, m_PluginInfo.Height, this, m_AudioCH, m_HostInfo);
  58. }
  59. void LFOPlugin::WriteWaves() {
  60. float RadCycle = (M_PI/180) * 360;
  61. float Pos = 0;
  62. float v = 0;
  63. float HalfTab = m_TableLength / 2;
  64. int QuatTab = m_TableLength / 4;
  65. int ThreeQuatTab = m_TableLength - QuatTab;
  66. int Shift;
  67. for (int n=0; n<m_TableLength; n++) {
  68. if (n==0) Pos = 0; else Pos = (n/(float)m_TableLength) * RadCycle;
  69. m_Table[SINE].Set (n, sin (Pos));
  70. if (n < QuatTab) Shift=n+ThreeQuatTab; else Shift=n-QuatTab;
  71. if (n<QuatTab || n>ThreeQuatTab) v = (((Shift-HalfTab) / HalfTab) * 2) - 1;
  72. else v = 1 - (Shift/HalfTab * 2);
  73. m_Table[TRIANGLE].Set (n, v);
  74. if (n<m_TableLength/2) m_Table[SQUARE].Set (n, 1.0f);
  75. else m_Table[SQUARE].Set (n, -1);
  76. m_Table[SAW].Set (n, 1.0f - (n / (float)m_TableLength) * 2.0f);
  77. }
  78. }
  79. float LFOPlugin::AdjustPos (float pos) {
  80. while (pos>=m_TableLength) pos -= m_TableLength;
  81. if (pos<0 || pos>=m_TableLength) pos = 0;
  82. return pos;
  83. }
  84. void LFOPlugin::Reset()
  85. {
  86. ResetPorts();
  87. for (int n=0; n<NUM_TABLES; n++)
  88. m_Table[n].Allocate (m_TableLength);
  89. WriteWaves();
  90. m_CyclePos = 0;
  91. m_Note = 0;
  92. }
  93. void LFOPlugin::Execute() {
  94. float Incr, Pos;
  95. for (int n=0; n<m_HostInfo->BUFSIZE; n++) {
  96. Incr = m_Freq * (m_TableLength / (float)m_HostInfo->SAMPLERATE);
  97. // Raw Output
  98. m_CyclePos = AdjustPos (m_CyclePos + Incr);
  99. SetOutput (0, n, m_Table[m_Type][m_CyclePos]);
  100. // 'Cosine' Output
  101. Pos = AdjustPos (m_CyclePos + (m_TableLength * 0.25));
  102. SetOutput (1, n, m_Table[m_Type][Pos]);
  103. // Inverted Output
  104. Pos = AdjustPos (m_TableLength - m_CyclePos);
  105. SetOutput (2, n, m_Table[m_Type][Pos]);
  106. }
  107. }
  108. void LFOPlugin::StreamOut(ostream &s) {
  109. s << m_Version << " " << (int)m_Type << " " << m_Freq << " ";
  110. }
  111. void LFOPlugin::StreamIn(istream &s) {
  112. int version;
  113. s >> version;
  114. s >> (int&)m_Type >> m_Freq;
  115. }