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.

335 lines
9.0KB

  1. /* SpiralPlugin
  2. * Copyleft (C) 2000 David Griffiths <dave@pawfal.org>
  3. * LADSPA Plugin by Nicolas Noble <nicolas@nobis-crew.org>
  4. *
  5. * This program is free software; you can redistribute it and/or modify
  6. * it under the terms of the GNU General Public License as published by
  7. * the Free Software Foundation; either version 2 of the License, or
  8. * (at your option) any later version.
  9. *
  10. * This program is distributed in the hope that it will be useful,
  11. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  12. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  13. * GNU General Public License for more details.
  14. *
  15. * You should have received a copy of the GNU General Public License
  16. * along with this program; if not, write to the Free Software
  17. * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
  18. */
  19. #include "LADSPAPluginGUI.h"
  20. #include <FL/fl_draw.h>
  21. #include <FL/fl_draw.H>
  22. #include "ladspa.h"
  23. #include <stdio.h>
  24. #include <math.h>
  25. #include <dlfcn.h>
  26. #include <vector>
  27. #include <algorithm>
  28. #include "utils.h"
  29. static const int GUI_COLOUR = 179;
  30. static const int GUIBG_COLOUR = 144;
  31. static const int GUIBG2_COLOUR = 145;
  32. ////////////////////////////////////////////
  33. /* FIXME: No matter what, I can't let this as it!! */
  34. static LADSPAPluginGUI * lg = NULL;
  35. void describePluginLibrary(const char * pcFullFilename, void * pvPluginHandle,
  36. LADSPA_Descriptor_Function pfDescriptorFunction) {
  37. const LADSPA_Descriptor * psDescriptor;
  38. long lIndex;
  39. unsigned long lPluginIndex;
  40. unsigned long lPortIndex;
  41. unsigned long lLength;
  42. LADSPA_PortRangeHintDescriptor iHintDescriptor;
  43. LADSPA_Data fBound;
  44. #define testcond(c,s) { \
  45. if (!(c)) { \
  46. cerr << (s); \
  47. failure = 1; \
  48. } \
  49. }
  50. for (lIndex = 0; (psDescriptor = pfDescriptorFunction(lIndex)) != NULL; lIndex++) {
  51. int failure = 0;
  52. testcond(!LADSPA_IS_REALTIME(psDescriptor->Properties), "ERROR: PLUGIN MUST RUN REAL TIME.\n");
  53. testcond(psDescriptor->instantiate, "ERROR: PLUGIN HAS NO INSTANTIATE FUNCTION.\n");
  54. testcond(psDescriptor->connect_port, "ERROR: PLUGIN HAS NO CONNECT_PORT FUNCTION.\n");
  55. testcond(psDescriptor->run, "ERROR: PLUGIN HAS NO RUN FUNCTION.\n");
  56. testcond(!(psDescriptor->run_adding != 0 && psDescriptor->set_run_adding_gain == 0),
  57. "ERROR: PLUGIN HAS RUN_ADDING FUNCTION BUT NOT SET_RUN_ADDING_GAIN.\n");
  58. testcond(!(psDescriptor->run_adding == 0 && psDescriptor->set_run_adding_gain != 0),
  59. "ERROR: PLUGIN HAS SET_RUN_ADDING_GAIN FUNCTION BUT NOT RUN_ADDING.\n");
  60. testcond(psDescriptor->cleanup, "ERROR: PLUGIN HAS NO CLEANUP FUNCTION.\n");
  61. testcond(!LADSPA_IS_INPLACE_BROKEN(psDescriptor->Properties),
  62. "ERROR: THIS PLUGIN CANNOT USE IN-PLACE PROCESSING.\n");
  63. testcond(psDescriptor->PortCount, "ERROR: PLUGIN HAS NO PORTS.\n");
  64. if (!failure) {
  65. LPluginInfo pi;
  66. pi.Filename = pcFullFilename;
  67. pi.Label = psDescriptor->Label;
  68. pi.Name = psDescriptor->Name;
  69. /* ARGH! I really can't stand this ugly hack */
  70. lg->PluginList.push_back(pi);
  71. } else {
  72. cerr << "Plugin ignored...\n\n";
  73. }
  74. }
  75. dlclose(pvPluginHandle);
  76. }
  77. void LADSPAPluginGUI::refreshPluginList(void)
  78. {
  79. PluginList.clear();
  80. CurrentPlugin.Name = "";
  81. CurrentPlugin.Filename = "";
  82. CurrentPlugin.Label = "";
  83. lg = this;
  84. LADSPAPluginSearch(describePluginLibrary);
  85. lg = NULL;
  86. m_Browser->clear();
  87. sort(PluginList.begin(), PluginList.end(), LPluginInfoSortAsc());
  88. for (vector<LPluginInfo>::iterator i = PluginList.begin(); i != PluginList.end(); i++)
  89. {
  90. m_Browser->add((*i).Name.c_str());
  91. }
  92. }
  93. LADSPAPluginGUI::LADSPAPluginGUI(int w, int h,LADSPAPlugin *o,const HostInfo *Info) :
  94. SpiralPluginGUI(w,h,o)
  95. {
  96. m_Filename="None";
  97. m_Plugin=o;
  98. int Width=20;
  99. int Height=100;
  100. m_Browser= new Fl_Hold_Browser(5,20,290,260,"LADSPA Plugins");
  101. m_Browser->callback((Fl_Callback*)cb_Select);
  102. m_InputScroll = new Fl_Scroll(300,80,290,150," Value Min Max Clamp?");
  103. m_InputScroll->align(FL_ALIGN_TOP_LEFT);
  104. m_InputScroll->type(Fl_Scroll::VERTICAL);
  105. m_InputScroll->box(FL_DOWN_BOX);
  106. add(m_InputScroll);
  107. m_InputPack = new Fl_Pack(300,85,300,100,"");
  108. m_InputScroll->add(m_InputPack);
  109. m_Name = new Fl_Box(290,20,10,20,"None");
  110. m_Name->align(FL_ALIGN_RIGHT);
  111. m_Name->labelcolor(GUI_COLOUR);
  112. m_Name->labelsize(10);
  113. add(m_Name);
  114. m_Maker = new Fl_Box(290,40,10,20,"None");
  115. m_Maker->align(FL_ALIGN_RIGHT);
  116. m_Maker->labelcolor(GUI_COLOUR);
  117. m_Maker->labelsize(10);
  118. add(m_Maker);
  119. m_OutputGain = new Fl_Knob(545,240,40,40,"Output Gain");
  120. m_OutputGain->color(GUI_COLOUR);
  121. m_OutputGain->type(Fl_Knob::DOTLIN);
  122. m_OutputGain->maximum(2);
  123. m_OutputGain->step(0.001);
  124. m_OutputGain->value(1.0);
  125. m_OutputGain->labelsize(10);
  126. m_OutputGain->callback((Fl_Callback*)cb_Gain);
  127. add(m_OutputGain);
  128. m_UpdateInputs = new Fl_Button(480,252,50,25,"Refresh");
  129. m_UpdateInputs->labelsize(10);
  130. m_UpdateInputs->value(1);
  131. m_UpdateInputs->type(1);
  132. add(m_UpdateInputs);
  133. m_UpdateMinMax = new Fl_Button(400,252,85,25,"Update Min/Max");
  134. m_UpdateMinMax->labelsize(10);
  135. m_UpdateMinMax->callback((Fl_Callback*)cb_MinMax);
  136. add(m_UpdateMinMax);
  137. m_PowerAmp = new Fl_Button(320,252,80,25,"PowerAmp");
  138. m_PowerAmp->labelsize(10);
  139. m_PowerAmp->value(0);
  140. m_PowerAmp->type(1);
  141. m_PowerAmp->callback((Fl_Callback*)cb_PowerAmp);
  142. add(m_PowerAmp);
  143. inited = 0;
  144. refreshPluginList();
  145. inited = 1;
  146. end();
  147. }
  148. LADSPAPluginGUI::~LADSPAPluginGUI(void)
  149. {
  150. Fl::check();
  151. }
  152. void LADSPAPluginGUI::UpdatePortDisplay(int n, float v)
  153. {
  154. if (!m_UpdateInputs->value()) return;
  155. char temp[256];
  156. sprintf(temp,"%f",v);
  157. m_PortOutput[n]->value(temp);
  158. }
  159. void LADSPAPluginGUI::SetMinMax(int n, float min, float max, bool clamp)
  160. {
  161. char temp[256];
  162. sprintf(temp,"%f",min);
  163. m_PortMin[n]->value(temp);
  164. sprintf(temp,"%f",max);
  165. m_PortMax[n]->value(temp);
  166. sprintf(temp, "%d",clamp);
  167. m_PortClamp[n]->value(atoi(temp));
  168. }
  169. void LADSPAPluginGUI::GetMinMax(int n, float &min, float &max, bool &clamp)
  170. {
  171. min = atof(m_PortMin[n]->value());
  172. max = atof(m_PortMax[n]->value());
  173. clamp = m_PortClamp[n]->value();
  174. }
  175. void LADSPAPluginGUI::SetName(const char *s)
  176. {
  177. m_Name->label(s);
  178. }
  179. void LADSPAPluginGUI::SetMaker(const char *s)
  180. {
  181. m_Maker->label(s);
  182. }
  183. void LADSPAPluginGUI::ClearPortInfo()
  184. {
  185. for (vector<Fl_Group*>::iterator i=m_PackVec.begin();
  186. i!=m_PackVec.end(); i++)
  187. {
  188. m_InputPack->remove((*i));
  189. }
  190. m_InputScroll->remove(m_InputPack);
  191. delete m_InputPack;
  192. m_InputPack = new Fl_Pack(300,85,300,100,"");
  193. m_InputScroll->add(m_InputPack);
  194. m_PortOutput.clear();
  195. m_PackVec.clear();
  196. m_PortMin.clear();
  197. m_PortMax.clear();
  198. m_PortClamp.clear();
  199. }
  200. void LADSPAPluginGUI::AddPortInfo(const char *Info)
  201. {
  202. Fl_Group* NewGroup = new Fl_Group(0,85,150,15,"");
  203. NewGroup->box(FL_FLAT_BOX);
  204. m_InputPack->add(NewGroup);
  205. m_PackVec.push_back(NewGroup);
  206. Fl_Box* NewText = new Fl_Box(100,85,80,15,"");
  207. NewText->label(Info);
  208. NewText->labelsize(8);
  209. NewText->align(FL_ALIGN_LEFT|FL_ALIGN_INSIDE);
  210. NewGroup->add(NewText);
  211. Fl_Output* NewOutput = new Fl_Output(5,85,20,15,"");
  212. NewOutput->value(0);
  213. NewOutput->textsize(10);
  214. NewGroup->add(NewOutput);
  215. m_PortOutput.push_back(NewOutput);
  216. Fl_Input* NewInput = new Fl_Input(26,85,20,15,"");
  217. NewInput->value(0);
  218. NewInput->textsize(10);
  219. NewGroup->add(NewInput);
  220. m_PortMin.push_back(NewInput);
  221. NewInput = new Fl_Input(47,85,20,15,"");
  222. NewInput->value(0);
  223. NewInput->textsize(10);
  224. NewGroup->add(NewInput);
  225. m_PortMax.push_back(NewInput);
  226. Fl_Check_Button* NewCheckButton = new Fl_Check_Button(80,85,15,15,"");
  227. NewCheckButton->value(0);
  228. NewGroup->add(NewCheckButton);
  229. m_PortClamp.push_back(NewCheckButton);
  230. NewGroup->redraw();
  231. m_InputPack->redraw();
  232. m_InputScroll->redraw();
  233. redraw();
  234. }
  235. void LADSPAPluginGUI::UpdateValues()
  236. {
  237. m_OutputGain->value(m_Plugin->GetGain());
  238. }
  239. inline void LADSPAPluginGUI::cb_Gain_i(Fl_Knob* o, void* v)
  240. { m_Plugin->SetGain(o->value()); }
  241. void LADSPAPluginGUI::cb_Gain(Fl_Knob* o, void* v)
  242. { ((LADSPAPluginGUI*)(o->parent()))->cb_Gain_i(o,v); }
  243. inline void LADSPAPluginGUI::cb_Select_i(Fl_Hold_Browser* o)
  244. {
  245. m_Filename=PluginList[o->value()-1].Filename;
  246. m_Label=PluginList[o->value()-1].Label;
  247. m_Plugin->UpdatePlugin(m_Filename.c_str(), m_Label.c_str());
  248. }
  249. void LADSPAPluginGUI::cb_Select(Fl_Hold_Browser* o)
  250. { ((LADSPAPluginGUI*)(o->parent()))->cb_Select_i(o);}
  251. inline void LADSPAPluginGUI::cb_MinMax_i(Fl_Button* o, void* v)
  252. {
  253. int n=0;
  254. for (vector<Fl_Input*>::iterator i=m_PortMin.begin();
  255. i!=m_PortMin.end(); i++)
  256. {
  257. m_Plugin->SetMin(n,atof((*i)->value()));
  258. n++;
  259. }
  260. n=0;
  261. for (vector<Fl_Input*>::iterator i=m_PortMax.begin();
  262. i!=m_PortMax.end(); i++)
  263. {
  264. m_Plugin->SetMax(n,atof((*i)->value()));
  265. n++;
  266. }
  267. n=0;
  268. for (vector<Fl_Check_Button*>::iterator i=m_PortClamp.begin();
  269. i!=m_PortClamp.end(); i++)
  270. {
  271. m_Plugin->SetPortClamp(n,(*i)->value());
  272. n++;
  273. }
  274. }
  275. void LADSPAPluginGUI::cb_MinMax(Fl_Button* o, void* v)
  276. { ((LADSPAPluginGUI*)(o->parent()))->cb_MinMax_i(o,v);}
  277. inline void LADSPAPluginGUI::cb_PowerAmp_i(Fl_Button* o, void* v)
  278. {
  279. m_Plugin->SetAmped(o->value());
  280. }
  281. void LADSPAPluginGUI::cb_PowerAmp(Fl_Button* o, void* v)
  282. { ((LADSPAPluginGUI*)(o->parent()))->cb_PowerAmp_i(o,v);}