Audio plugin host https://kx.studio/carla
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.

carla_skin.py 73KB

10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
11 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
10 years ago
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683168416851686168716881689169016911692169316941695169616971698169917001701170217031704170517061707170817091710171117121713171417151716171717181719172017211722172317241725172617271728172917301731173217331734173517361737173817391740174117421743174417451746174717481749175017511752175317541755175617571758175917601761176217631764176517661767176817691770177117721773177417751776177717781779178017811782178317841785178617871788178917901791179217931794179517961797179817991800180118021803180418051806180718081809181018111812181318141815181618171818181918201821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890189118921893189418951896189718981899190019011902190319041905190619071908190919101911191219131914191519161917191819191920192119221923192419251926192719281929193019311932193319341935193619371938193919401941194219431944194519461947194819491950195119521953195419551956195719581959196019611962196319641965196619671968196919701971197219731974197519761977197819791980198119821983
  1. #!/usr/bin/env python3
  2. # -*- coding: utf-8 -*-
  3. # Carla plugin/slot skin code
  4. # Copyright (C) 2013-2014 Filipe Coelho <falktx@falktx.com>
  5. #
  6. # This program is free software; you can redistribute it and/or
  7. # modify it under the terms of the GNU General Public License as
  8. # published by the Free Software Foundation; either version 2 of
  9. # the License, or any later version.
  10. #
  11. # This program is distributed in the hope that it will be useful,
  12. # but WITHOUT ANY WARRANTY; without even the implied warranty of
  13. # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  14. # GNU General Public License for more details.
  15. #
  16. # For a full copy of the GNU General Public License see the doc/GPL.txt file.
  17. # ------------------------------------------------------------------------------------------------------------
  18. # Imports (Config)
  19. from carla_config import *
  20. # ------------------------------------------------------------------------------------------------------------
  21. # Imports (Global)
  22. if config_UseQt5:
  23. from PyQt5.QtCore import Qt, QRectF
  24. from PyQt5.QtGui import QFont, QFontDatabase, QPen, QPixmap
  25. from PyQt5.QtWidgets import QFrame, QPushButton
  26. else:
  27. from PyQt4.QtCore import Qt, QRectF
  28. from PyQt4.QtGui import QFont, QFontDatabase, QFrame, QPen, QPixmap, QPushButton
  29. # ------------------------------------------------------------------------------------------------------------
  30. # Imports (Custom)
  31. import ui_carla_plugin_default
  32. import ui_carla_plugin_basic_fx
  33. import ui_carla_plugin_calf
  34. import ui_carla_plugin_sf2
  35. import ui_carla_plugin_zita
  36. import ui_carla_plugin_zynfx
  37. from carla_widgets import *
  38. from digitalpeakmeter import DigitalPeakMeter
  39. from pixmapdial import PixmapDial
  40. # ------------------------------------------------------------------------------------------------------------
  41. # Try to "shortify" a parameter name
  42. def getParameterShortName(paramName):
  43. paramName = paramName.split("/",1)[0].split(" (",1)[0].split(" [",1)[0].strip()
  44. paramLow = paramName.lower()
  45. if paramLow.startswith("compressor "):
  46. paramName = paramName.replace("ompressor ", ".", 1)
  47. paramLow = paramName.lower()
  48. # Cut generic names
  49. if "attack" in paramLow:
  50. paramName = paramName.replace("ttack", "tk")
  51. elif "bandwidth" in paramLow:
  52. paramName = paramName.replace("andwidth", "w")
  53. elif "damping" in paramLow:
  54. paramName = paramName.replace("amping", "amp")
  55. elif "distortion" in paramLow:
  56. paramName = paramName.replace("istortion", "ist")
  57. elif "feedback" in paramLow:
  58. paramName = paramName.replace("eedback", "b")
  59. elif "frequency" in paramLow:
  60. paramName = paramName.replace("requency", "req")
  61. elif "makeup" in paramLow:
  62. paramName = paramName.replace("akeup", "kUp" if "Make" in paramName else "kup")
  63. elif "output" in paramLow:
  64. paramName = paramName.replace("utput", "ut")
  65. elif "random" in paramLow:
  66. paramName = paramName.replace("andom", "nd")
  67. elif "threshold" in paramLow:
  68. paramName = paramName.replace("hreshold", "hres")
  69. # Cut useless prefix
  70. elif paramLow.startswith("room "):
  71. paramName = paramName.split(" ",1)[1]
  72. # Cut useless suffix
  73. elif paramLow.endswith(" level"):
  74. paramName = paramName.rsplit(" ",1)[0]
  75. elif paramLow.endswith(" time"):
  76. paramName = paramName.rsplit(" ",1)[0]
  77. if len(paramName) > 7:
  78. paramName = paramName[:7]
  79. return paramName.strip()
  80. # ------------------------------------------------------------------------------------------------------------
  81. # Abstract plugin slot
  82. class AbstractPluginSlot(QFrame, PluginEditParentMeta):
  83. #class AbstractPluginSlot(QFrame, PluginEditParentMeta, metaclass=PyQtMetaClass):
  84. def __init__(self, parent, host, pluginId):
  85. QFrame.__init__(self, parent)
  86. self.host = host
  87. if False:
  88. # kdevelop likes this :)
  89. host = CarlaHostMeta()
  90. self.host = host
  91. # -------------------------------------------------------------
  92. # Get plugin info
  93. self.fPluginId = pluginId
  94. self.fPluginInfo = host.get_plugin_info(self.fPluginId)
  95. #if not gCarla.isLocal:
  96. #self.fPluginInfo['hints'] &= ~PLUGIN_HAS_CUSTOM_UI
  97. # -------------------------------------------------------------
  98. # Internal stuff
  99. self.fIsActive = bool(host.get_internal_parameter_value(self.fPluginId, PARAMETER_ACTIVE) >= 0.5)
  100. self.fIsSelected = False
  101. self.fLastGreenLedState = False
  102. self.fLastBlueLedState = False
  103. self.fParameterIconTimer = ICON_STATE_OFF
  104. self.fParameterList = [] # index, widget
  105. if host.processMode == ENGINE_PROCESS_MODE_CONTINUOUS_RACK:
  106. self.fPeaksInputCount = 2
  107. self.fPeaksOutputCount = 2
  108. else:
  109. audioCountInfo = host.get_audio_port_count_info(self.fPluginId)
  110. self.fPeaksInputCount = int(audioCountInfo['ins'])
  111. self.fPeaksOutputCount = int(audioCountInfo['outs'])
  112. if self.fPeaksInputCount > 2:
  113. self.fPeaksInputCount = 2
  114. if self.fPeaksOutputCount > 2:
  115. self.fPeaksOutputCount = 2
  116. # used during testing
  117. self.fIdleTimerId = 0
  118. # -------------------------------------------------------------
  119. # Set-up GUI
  120. self.fEditDialog = PluginEdit(self, host, self.fPluginId)
  121. # -------------------------------------------------------------
  122. # Set-up common widgets (as none)
  123. self.b_enable = None
  124. self.b_gui = None
  125. self.b_edit = None
  126. self.b_remove = None
  127. self.cb_presets = None
  128. self.label_name = None
  129. self.label_type = None
  130. self.led_control = None
  131. self.led_midi = None
  132. self.led_audio_in = None
  133. self.led_audio_out = None
  134. self.peak_in = None
  135. self.peak_out = None
  136. # -------------------------------------------------------------
  137. # Set-up connections
  138. host.PluginRenamedCallback.connect(self.slot_handlePluginRenamedCallback)
  139. host.PluginUnavailableCallback.connect(self.slot_handlePluginUnavailableCallback)
  140. host.ParameterValueChangedCallback.connect(self.slot_handleParameterValueChangedCallback)
  141. host.ParameterDefaultChangedCallback.connect(self.slot_handleParameterDefaultChangedCallback)
  142. host.ParameterMidiChannelChangedCallback.connect(self.slot_handleParameterMidiChannelChangedCallback)
  143. host.ParameterMidiCcChangedCallback.connect(self.slot_handleParameterMidiCcChangedCallback)
  144. host.ProgramChangedCallback.connect(self.slot_handleProgramChangedCallback)
  145. host.MidiProgramChangedCallback.connect(self.slot_handleMidiProgramChangedCallback)
  146. host.OptionChangedCallback.connect(self.slot_handleOptionChangedCallback)
  147. host.UiStateChangedCallback.connect(self.slot_handleUiStateChangedCallback)
  148. # -----------------------------------------------------------------
  149. @pyqtSlot(int, str)
  150. def slot_handlePluginRenamedCallback(self, pluginId, newName):
  151. if self.fPluginId == pluginId:
  152. self.setName(newName)
  153. @pyqtSlot(int, str)
  154. def slot_handlePluginUnavailableCallback(self, pluginId, errorMsg):
  155. if self.fPluginId == pluginId:
  156. pass
  157. @pyqtSlot(int, int, float)
  158. def slot_handleParameterValueChangedCallback(self, pluginId, index, value):
  159. if self.fPluginId == pluginId:
  160. self.setParameterValue(index, value, True)
  161. @pyqtSlot(int, int, float)
  162. def slot_handleParameterDefaultChangedCallback(self, pluginId, index, value):
  163. if self.fPluginId == pluginId:
  164. self.setParameterDefault(index, value)
  165. @pyqtSlot(int, int, int)
  166. def slot_handleParameterMidiCcChangedCallback(self, pluginId, index, cc):
  167. if self.fPluginId == pluginId:
  168. self.setParameterMidiControl(index, cc)
  169. @pyqtSlot(int, int, int)
  170. def slot_handleParameterMidiChannelChangedCallback(self, pluginId, index, channel):
  171. if self.fPluginId == pluginId:
  172. self.setParameterMidiChannel(index, channel)
  173. @pyqtSlot(int, int)
  174. def slot_handleProgramChangedCallback(self, pluginId, index):
  175. if self.fPluginId == pluginId:
  176. self.setProgram(index, True)
  177. @pyqtSlot(int, int)
  178. def slot_handleMidiProgramChangedCallback(self, pluginId, index):
  179. if self.fPluginId == pluginId:
  180. self.setMidiProgram(index, True)
  181. @pyqtSlot(int, int, bool)
  182. def slot_handleOptionChangedCallback(self, pluginId, option, yesNo):
  183. if self.fPluginId == pluginId:
  184. self.setOption(option, yesNo)
  185. @pyqtSlot(int, int)
  186. def slot_handleUiStateChangedCallback(self, pluginId, state):
  187. if self.fPluginId == pluginId:
  188. self.customUiStateChanged(state)
  189. #------------------------------------------------------------------
  190. def ready(self):
  191. if self.b_enable is not None:
  192. self.b_enable.setChecked(self.fIsActive)
  193. self.b_enable.clicked.connect(self.slot_enableClicked)
  194. if self.b_gui is not None:
  195. self.b_gui.clicked.connect(self.slot_showCustomUi)
  196. self.b_gui.setEnabled(bool(self.fPluginInfo['hints'] & PLUGIN_HAS_CUSTOM_UI))
  197. if self.b_edit is None:
  198. # Edit dialog *must* be available
  199. self.b_edit = QPushButton(self)
  200. self.b_edit.setCheckable(True)
  201. self.b_edit.hide()
  202. self.b_edit.clicked.connect(self.slot_showEditDialog)
  203. if self.b_remove is not None:
  204. self.b_remove.clicked.connect(self.slot_removePlugin)
  205. if self.label_name is not None:
  206. self.label_name.setText(self.fPluginInfo['name'])
  207. if self.label_type is not None:
  208. self.label_type.setText(getPluginTypeAsString(self.fPluginInfo['type']))
  209. if self.led_control is not None:
  210. self.led_control.setColor(self.led_control.YELLOW)
  211. self.led_control.setEnabled(False)
  212. if self.led_midi is not None:
  213. self.led_midi.setColor(self.led_midi.RED)
  214. self.led_midi.setEnabled(False)
  215. if self.led_audio_in is not None:
  216. self.led_audio_in.setColor(self.led_audio_in.GREEN)
  217. self.led_audio_in.setEnabled(False)
  218. if self.led_audio_out is not None:
  219. self.led_audio_out.setColor(self.led_audio_out.BLUE)
  220. self.led_audio_out.setEnabled(False)
  221. if self.peak_in is not None:
  222. self.peak_in.setColor(DigitalPeakMeter.GREEN)
  223. self.peak_in.setChannels(self.fPeaksInputCount)
  224. self.peak_in.setOrientation(DigitalPeakMeter.HORIZONTAL)
  225. if self.peak_out is not None:
  226. self.peak_out.setColor(DigitalPeakMeter.BLUE)
  227. self.peak_out.setChannels(self.fPeaksOutputCount)
  228. self.peak_out.setOrientation(DigitalPeakMeter.HORIZONTAL)
  229. for paramIndex, paramWidget in self.fParameterList:
  230. paramWidget.setContextMenuPolicy(Qt.CustomContextMenu)
  231. paramWidget.customContextMenuRequested.connect(self.slot_knobCustomMenu)
  232. paramWidget.realValueChanged.connect(self.slot_parameterValueChanged)
  233. paramWidget.setValue(self.host.get_internal_parameter_value(self.fPluginId, paramIndex))
  234. self.setWindowTitle(self.fPluginInfo['name'])
  235. #------------------------------------------------------------------
  236. def getFixedHeight(self):
  237. return 32
  238. def getHints(self):
  239. return self.fPluginInfo['hints']
  240. def getPluginId(self):
  241. return self.fPluginId
  242. #------------------------------------------------------------------
  243. def setPluginId(self, idx):
  244. self.fPluginId = idx
  245. self.fEditDialog.setPluginId(idx)
  246. def setName(self, name):
  247. self.fEditDialog.setName(name)
  248. if self.label_name is not None:
  249. self.label_name.setText(name)
  250. def setSelected(self, yesNo):
  251. if self.fIsSelected == yesNo:
  252. return
  253. self.fIsSelected = yesNo
  254. self.update()
  255. #------------------------------------------------------------------
  256. def setActive(self, active, sendCallback=False, sendHost=True):
  257. self.fIsActive = active
  258. if sendCallback:
  259. self.fParameterIconTimer = ICON_STATE_ON
  260. self.activeChanged(active)
  261. if sendHost:
  262. self.host.set_active(self.fPluginId, active)
  263. if active:
  264. self.fEditDialog.clearNotes()
  265. self.midiActivityChanged(False)
  266. # called from rack, checks if param is possible first
  267. def setInternalParameter(self, parameterId, value):
  268. if parameterId <= PARAMETER_MAX or parameterId >= PARAMETER_NULL:
  269. return
  270. elif parameterId == PARAMETER_ACTIVE:
  271. return self.setActive(bool(value), True, True)
  272. elif parameterId == PARAMETER_DRYWET:
  273. if (self.fPluginInfo['hints'] & PLUGIN_CAN_DRYWET) == 0: return
  274. self.host.set_drywet(self.fPluginId, value)
  275. elif parameterId == PARAMETER_VOLUME:
  276. if (self.fPluginInfo['hints'] & PLUGIN_CAN_VOLUME) == 0: return
  277. self.host.set_volume(self.fPluginId, value)
  278. elif parameterId == PARAMETER_BALANCE_LEFT:
  279. if (self.fPluginInfo['hints'] & PLUGIN_CAN_BALANCE) == 0: return
  280. self.host.set_balance_left(self.fPluginId, value)
  281. elif parameterId == PARAMETER_BALANCE_RIGHT:
  282. if (self.fPluginInfo['hints'] & PLUGIN_CAN_BALANCE) == 0: return
  283. self.host.set_balance_right(self.fPluginId, value)
  284. elif parameterId == PARAMETER_PANNING:
  285. if (self.fPluginInfo['hints'] & PLUGIN_CAN_PANNING) == 0: return
  286. self.host.set_panning(self.fPluginId, value)
  287. elif parameterId == PARAMETER_CTRL_CHANNEL:
  288. self.host.set_ctrl_channel(self.fPluginId, value)
  289. self.fEditDialog.setParameterValue(parameterId, value)
  290. #------------------------------------------------------------------
  291. def setParameterValue(self, parameterId, value, sendCallback):
  292. if parameterId == PARAMETER_ACTIVE:
  293. return self.setActive(bool(value), True, False)
  294. self.fEditDialog.setParameterValue(parameterId, value)
  295. if sendCallback:
  296. self.fParameterIconTimer = ICON_STATE_ON
  297. self.editDialogParameterValueChanged(self.fPluginId, parameterId, value)
  298. def setParameterDefault(self, parameterId, value):
  299. self.fEditDialog.setParameterDefault(parameterId, value)
  300. def setParameterMidiControl(self, parameterId, control):
  301. self.fEditDialog.setParameterMidiControl(parameterId, control)
  302. def setParameterMidiChannel(self, parameterId, channel):
  303. self.fEditDialog.setParameterMidiChannel(parameterId, channel)
  304. #------------------------------------------------------------------
  305. def setProgram(self, index, sendCallback):
  306. self.fEditDialog.setProgram(index)
  307. if sendCallback:
  308. self.fParameterIconTimer = ICON_STATE_ON
  309. self.editDialogProgramChanged(self.fPluginId, index)
  310. def setMidiProgram(self, index, sendCallback):
  311. self.fEditDialog.setMidiProgram(index)
  312. if sendCallback:
  313. self.fParameterIconTimer = ICON_STATE_ON
  314. self.editDialogMidiProgramChanged(self.fPluginId, index)
  315. #------------------------------------------------------------------
  316. def setOption(self, option, yesNo):
  317. self.fEditDialog.setOption(option, yesNo)
  318. #------------------------------------------------------------------
  319. def activeChanged(self, onOff):
  320. self.fIsActive = onOff
  321. if self.b_enable is None:
  322. return
  323. self.b_enable.blockSignals(True)
  324. self.b_enable.setChecked(onOff)
  325. self.b_enable.blockSignals(False)
  326. def customUiStateChanged(self, state):
  327. if self.b_gui is None:
  328. return
  329. self.b_gui.blockSignals(True)
  330. if state == 0:
  331. self.b_gui.setChecked(False)
  332. self.b_gui.setEnabled(True)
  333. elif state == 1:
  334. self.b_gui.setChecked(True)
  335. self.b_gui.setEnabled(True)
  336. elif state == -1:
  337. self.b_gui.setChecked(False)
  338. self.b_gui.setEnabled(False)
  339. self.b_gui.blockSignals(False)
  340. def parameterActivityChanged(self, onOff):
  341. if self.led_control is None:
  342. return
  343. self.led_control.setChecked(onOff)
  344. def midiActivityChanged(self, onOff):
  345. if self.led_midi is None:
  346. return
  347. self.led_midi.setChecked(onOff)
  348. def optionChanged(self, option, yesNo):
  349. pass
  350. # -----------------------------------------------------------------
  351. # PluginEdit callbacks
  352. def editDialogVisibilityChanged(self, pluginId, visible):
  353. if self.b_edit is None:
  354. return
  355. self.b_edit.blockSignals(True)
  356. self.b_edit.setChecked(visible)
  357. self.b_edit.blockSignals(False)
  358. def editDialogPluginHintsChanged(self, pluginId, hints):
  359. self.fPluginInfo['hints'] = hints
  360. for paramIndex, paramWidget in self.fParameterList:
  361. if paramIndex == PARAMETER_DRYWET:
  362. paramWidget.setVisible(hints & PLUGIN_CAN_DRYWET)
  363. elif paramIndex == PARAMETER_VOLUME:
  364. paramWidget.setVisible(hints & PLUGIN_CAN_VOLUME)
  365. if self.b_gui is not None:
  366. self.b_gui.setEnabled(bool(hints & PLUGIN_HAS_CUSTOM_UI))
  367. def editDialogParameterValueChanged(self, pluginId, parameterId, value):
  368. for paramIndex, paramWidget in self.fParameterList:
  369. if paramIndex != parameterId:
  370. continue
  371. paramWidget.blockSignals(True)
  372. paramWidget.setValue(value)
  373. paramWidget.blockSignals(False)
  374. break
  375. def editDialogProgramChanged(self, pluginId, index):
  376. if self.cb_presets is None:
  377. return
  378. self.cb_presets.blockSignals(True)
  379. self.cb_presets.setCurrentIndex(index)
  380. self.cb_presets.blockSignals(False)
  381. def editDialogMidiProgramChanged(self, pluginId, index):
  382. if self.cb_presets is None:
  383. return
  384. self.cb_presets.blockSignals(True)
  385. self.cb_presets.setCurrentIndex(index)
  386. self.cb_presets.blockSignals(False)
  387. def editDialogNotePressed(self, pluginId, note):
  388. pass
  389. def editDialogNoteReleased(self, pluginId, note):
  390. pass
  391. def editDialogMidiActivityChanged(self, pluginId, onOff):
  392. self.midiActivityChanged(onOff)
  393. #------------------------------------------------------------------
  394. def idleFast(self):
  395. # Input peaks
  396. if self.fPeaksInputCount > 0:
  397. if self.fPeaksInputCount > 1:
  398. peak1 = self.host.get_input_peak_value(self.fPluginId, True)
  399. peak2 = self.host.get_input_peak_value(self.fPluginId, False)
  400. ledState = bool(peak1 != 0.0 or peak2 != 0.0)
  401. if self.peak_in is not None:
  402. self.peak_in.displayMeter(1, peak1)
  403. self.peak_in.displayMeter(2, peak2)
  404. else:
  405. peak = self.host.get_input_peak_value(self.fPluginId, True)
  406. ledState = bool(peak != 0.0)
  407. if self.peak_in is not None:
  408. self.peak_in.displayMeter(1, peak)
  409. if self.fLastGreenLedState != ledState and self.led_audio_in is not None:
  410. self.fLastGreenLedState = ledState
  411. self.led_audio_in.setChecked(ledState)
  412. # Output peaks
  413. if self.fPeaksOutputCount > 0:
  414. if self.fPeaksOutputCount > 1:
  415. peak1 = self.host.get_output_peak_value(self.fPluginId, True)
  416. peak2 = self.host.get_output_peak_value(self.fPluginId, False)
  417. ledState = bool(peak1 != 0.0 or peak2 != 0.0)
  418. if self.peak_out is not None:
  419. self.peak_out.displayMeter(1, peak1)
  420. self.peak_out.displayMeter(2, peak2)
  421. else:
  422. peak = self.host.get_output_peak_value(self.fPluginId, True)
  423. ledState = bool(peak != 0.0)
  424. if self.peak_out is not None:
  425. self.peak_out.displayMeter(1, peak)
  426. if self.fLastBlueLedState != ledState and self.led_audio_out is not None:
  427. self.fLastBlueLedState = ledState
  428. self.led_audio_out.setChecked(ledState)
  429. def idleSlow(self):
  430. if self.fParameterIconTimer == ICON_STATE_ON:
  431. self.fParameterIconTimer = ICON_STATE_WAIT1
  432. self.parameterActivityChanged(True)
  433. elif self.fParameterIconTimer == ICON_STATE_WAIT1:
  434. self.fParameterIconTimer = ICON_STATE_WAIT2
  435. elif self.fParameterIconTimer == ICON_STATE_WAIT2:
  436. self.fParameterIconTimer = ICON_STATE_OFF
  437. self.parameterActivityChanged(False)
  438. self.fEditDialog.idleSlow()
  439. #------------------------------------------------------------------
  440. def drawOutline(self):
  441. painter = QPainter(self)
  442. if self.fIsSelected:
  443. painter.setPen(QPen(Qt.cyan, 4))
  444. painter.setBrush(Qt.transparent)
  445. painter.drawRect(0, 0, self.width(), self.height())
  446. else:
  447. painter.setPen(QPen(Qt.black, 1))
  448. painter.setBrush(Qt.black)
  449. painter.drawLine(0, self.height()-1, self.width(), self.height()-1)
  450. def showDefaultCustomMenu(self, isEnabled, bEdit = None, bGui = None):
  451. menu = QMenu(self)
  452. actActive = menu.addAction(self.tr("Disable") if isEnabled else self.tr("Enable"))
  453. menu.addSeparator()
  454. actReset = menu.addAction(self.tr("Reset parameters"))
  455. actRandom = menu.addAction(self.tr("Randomize parameters"))
  456. menu.addSeparator()
  457. if bEdit is not None:
  458. actEdit = menu.addAction(self.tr("Edit"))
  459. actEdit.setCheckable(True)
  460. actEdit.setChecked(bEdit.isChecked())
  461. else:
  462. actEdit = None
  463. if bGui is not None:
  464. actGui = menu.addAction(self.tr("Show Custom UI"))
  465. actGui.setCheckable(True)
  466. actGui.setChecked(bGui.isChecked())
  467. actGui.setEnabled(bGui.isEnabled())
  468. else:
  469. actGui = None
  470. menu.addSeparator()
  471. actClone = menu.addAction(self.tr("Clone"))
  472. actReplace = menu.addAction(self.tr("Replace..."))
  473. actRename = menu.addAction(self.tr("Rename..."))
  474. actRemove = menu.addAction(self.tr("Remove"))
  475. if self.fIdleTimerId != 0:
  476. actRemove.setVisible(False)
  477. actSel = menu.exec_(QCursor.pos())
  478. if not actSel:
  479. return
  480. if actSel == actActive:
  481. self.setActive(not isEnabled, True, True)
  482. elif actSel == actReset:
  483. self.host.reset_parameters(self.fPluginId)
  484. elif actSel == actRandom:
  485. self.host.randomize_parameters(self.fPluginId)
  486. elif actSel == actGui:
  487. bGui.click()
  488. elif actSel == actEdit:
  489. bEdit.click()
  490. elif actSel == actClone:
  491. if not self.host.clone_plugin(self.fPluginId):
  492. CustomMessageBox(self, QMessageBox.Warning, self.tr("Error"), self.tr("Operation failed"),
  493. self.host.get_last_error(), QMessageBox.Ok, QMessageBox.Ok)
  494. elif actSel == actRename:
  495. oldName = self.fPluginInfo['name']
  496. newNameTry = QInputDialog.getText(self, self.tr("Rename Plugin"), self.tr("New plugin name:"), QLineEdit.Normal, oldName)
  497. if not (newNameTry[1] and newNameTry[0] and oldName != newNameTry[0]):
  498. return
  499. newName = newNameTry[0]
  500. if self.host.rename_plugin(self.fPluginId, newName):
  501. self.setName(newName)
  502. else:
  503. CustomMessageBox(self, QMessageBox.Warning, self.tr("Error"), self.tr("Operation failed"),
  504. self.host.get_last_error(), QMessageBox.Ok, QMessageBox.Ok)
  505. elif actSel == actReplace:
  506. gCarla.gui.slot_pluginAdd(self.fPluginId)
  507. elif actSel == actRemove:
  508. if not self.host.remove_plugin(self.fPluginId):
  509. CustomMessageBox(self, QMessageBox.Warning, self.tr("Error"), self.tr("Operation failed"),
  510. self.host.get_last_error(), QMessageBox.Ok, QMessageBox.Ok)
  511. #------------------------------------------------------------------
  512. @pyqtSlot(bool)
  513. def slot_enableClicked(self, yesNo):
  514. self.setActive(yesNo, False, True)
  515. @pyqtSlot()
  516. def slot_showDefaultCustomMenu(self):
  517. self.showDefaultCustomMenu(self.fIsActive, self.b_edit, self.b_gui)
  518. @pyqtSlot()
  519. def slot_knobCustomMenu(self):
  520. sender = self.sender()
  521. index = sender.fIndex
  522. minimum = sender.fMinimum
  523. maximum = sender.fMaximum
  524. current = sender.fRealValue
  525. label = sender.fLabel
  526. if index in (PARAMETER_DRYWET, PARAMETER_VOLUME):
  527. default = 1.0
  528. resetText = self.tr("Reset (%i%%)" % int(default*100.0))
  529. minimText = self.tr("Set to Minimum (%i%%)" % int(minimum*100.0))
  530. maximText = self.tr("Set to Maximum (%i%%)" % int(maximum*100.0))
  531. else:
  532. default = self.host.get_default_parameter_value(self.fPluginId, index)
  533. resetText = self.tr("Reset (%f)" % default)
  534. minimText = self.tr("Set to Minimum (%f)" % minimum)
  535. maximText = self.tr("Set to Maximum (%f)" % maximum)
  536. menu = QMenu(self)
  537. actReset = menu.addAction(resetText)
  538. menu.addSeparator()
  539. actMinimum = menu.addAction(minimText)
  540. actMaximum = menu.addAction(maximText)
  541. menu.addSeparator()
  542. actSet = menu.addAction(self.tr("Set value..."))
  543. actSelected = menu.exec_(QCursor.pos())
  544. if actSelected == actSet:
  545. valueTry = QInputDialog.getDouble(self, self.tr("Set value"), label, current, minimum, maximum, 3) # FIXME - 3 decimals
  546. if valueTry[1]:
  547. value = valueTry[0] * 10
  548. else:
  549. return
  550. elif actSelected == actMinimum:
  551. value = minimum
  552. elif actSelected == actMaximum:
  553. value = maximum
  554. elif actSelected == actReset:
  555. value = default
  556. else:
  557. return
  558. self.sender().setValue(value)
  559. #------------------------------------------------------------------
  560. @pyqtSlot(bool)
  561. def slot_showCustomUi(self, show):
  562. self.host.show_custom_ui(self.fPluginId, show)
  563. @pyqtSlot(bool)
  564. def slot_showEditDialog(self, show):
  565. self.fEditDialog.setVisible(show)
  566. @pyqtSlot()
  567. def slot_removePlugin(self):
  568. self.host.remove_plugin(self.fPluginId)
  569. #------------------------------------------------------------------
  570. @pyqtSlot(int)
  571. def slot_parameterValueChanged(self, value):
  572. index = self.sender().getIndex()
  573. if index < 0:
  574. self.setInternalParameter(index, value)
  575. else:
  576. self.host.set_parameter_value(self.fPluginId, index, value)
  577. self.setParameterValue(index, value, False)
  578. @pyqtSlot(int)
  579. def slot_programChanged(self, index):
  580. self.host.set_program(self.fPluginId, index)
  581. self.setProgram(index, False)
  582. @pyqtSlot(int)
  583. def slot_midiProgramChanged(self, index):
  584. self.host.set_midi_program(self.fPluginId, index)
  585. self.setMidiProgram(index, False)
  586. #------------------------------------------------------------------
  587. def testTimer(self):
  588. self.fIdleTimerId = self.startTimer(25)
  589. #------------------------------------------------------------------
  590. def closeEvent(self, event):
  591. if self.fIdleTimerId != 0:
  592. self.killTimer(self.fIdleTimerId)
  593. self.fIdleTimerId = 0
  594. self.host.engine_close()
  595. QFrame.closeEvent(self, event)
  596. def timerEvent(self, event):
  597. if event.timerId() == self.fIdleTimerId:
  598. self.host.engine_idle()
  599. self.idleFast()
  600. self.idleSlow()
  601. QFrame.timerEvent(self, event)
  602. def paintEvent(self, event):
  603. self.drawOutline()
  604. QFrame.paintEvent(self, event)
  605. # ------------------------------------------------------------------------------------------------------------
  606. class PluginSlot_Default(AbstractPluginSlot):
  607. def __init__(self, parent, host, pluginId):
  608. AbstractPluginSlot.__init__(self, parent, host, pluginId)
  609. self.ui = ui_carla_plugin_default.Ui_PluginWidget()
  610. self.ui.setupUi(self)
  611. # -------------------------------------------------------------
  612. # Internal stuff
  613. self.fColorTop = QColor(60, 60, 60)
  614. self.fColorBottom = QColor(47, 47, 47)
  615. self.fColorSeprtr = QColor(70, 70, 70)
  616. # -------------------------------------------------------------
  617. # Set-up GUI
  618. self.setStyleSheet("""
  619. QLabel#label_name {
  620. color: #BBB;
  621. }
  622. """)
  623. self.ui.b_enable.setPixmaps(":/bitmaps/button_off.png", ":/bitmaps/button_on.png", ":/bitmaps/button_off.png")
  624. self.ui.b_edit.setPixmaps(":/bitmaps/button_edit.png", ":/bitmaps/button_edit_down.png", ":/bitmaps/button_edit_hover.png")
  625. if self.fPluginInfo['iconName'] == "distrho":
  626. self.ui.b_gui.setPixmaps(":/bitmaps/button_distrho.png", ":/bitmaps/button_distrho_down.png", ":/bitmaps/button_distrho_hover.png")
  627. elif self.fPluginInfo['iconName'] == "file":
  628. self.ui.b_gui.setPixmaps(":/bitmaps/button_file.png", ":/bitmaps/button_file_down.png", ":/bitmaps/button_file_hover.png")
  629. else:
  630. self.ui.b_gui.setPixmaps(":/bitmaps/button_gui.png", ":/bitmaps/button_gui_down.png", ":/bitmaps/button_gui_hover.png")
  631. # -------------------------------------------------------------
  632. self.b_enable = self.ui.b_enable
  633. self.b_gui = self.ui.b_gui
  634. self.b_edit = self.ui.b_edit
  635. self.label_name = self.ui.label_name
  636. self.led_control = self.ui.led_control
  637. self.led_midi = self.ui.led_midi
  638. self.led_audio_in = self.ui.led_audio_in
  639. self.led_audio_out = self.ui.led_audio_out
  640. self.peak_in = self.ui.peak_in
  641. self.peak_out = self.ui.peak_out
  642. self.ready()
  643. self.customContextMenuRequested.connect(self.slot_showDefaultCustomMenu)
  644. #------------------------------------------------------------------
  645. def getFixedHeight(self):
  646. return 36
  647. #------------------------------------------------------------------
  648. def paintEvent(self, event):
  649. painter = QPainter(self)
  650. painter.save()
  651. areaX = self.ui.area_right.x()+7
  652. width = self.width()
  653. height = self.height()
  654. painter.setPen(QPen(QColor(17, 17, 17), 1))
  655. painter.setBrush(QColor(17, 17, 17))
  656. painter.drawRect(0, 0, width, height)
  657. painter.setPen(self.fColorSeprtr.lighter(110))
  658. painter.setBrush(self.fColorBottom)
  659. painter.setRenderHint(QPainter.Antialiasing, True)
  660. # name -> leds arc
  661. path = QPainterPath()
  662. path.moveTo(areaX-20, height-4)
  663. path.cubicTo(areaX, height-5, areaX-20, 4.75, areaX, 4.75)
  664. path.lineTo(areaX, height-5)
  665. painter.drawPath(path)
  666. painter.setPen(self.fColorSeprtr)
  667. painter.setRenderHint(QPainter.Antialiasing, False)
  668. # separator lines
  669. painter.drawLine(0, height-5, areaX-20, height-5)
  670. painter.drawLine(areaX, 4, width, 4)
  671. painter.setPen(self.fColorBottom)
  672. painter.setBrush(self.fColorBottom)
  673. # top, bottom and left lines
  674. painter.drawLine(0, 0, width, 0)
  675. painter.drawRect(0, height-4, areaX, 4)
  676. painter.drawRoundedRect(areaX-20, height-5, areaX, 5, 22, 22)
  677. painter.drawLine(0, 0, 0, height)
  678. # fill the rest
  679. painter.drawRect(areaX-1, 5, width, height)
  680. # bottom 1px line
  681. painter.setPen(self.fColorSeprtr)
  682. painter.drawLine(0, height-1, width, height-1)
  683. painter.restore()
  684. AbstractPluginSlot.paintEvent(self, event)
  685. # ------------------------------------------------------------------------------------------------------------
  686. class PluginSlot_BasicFX(AbstractPluginSlot):
  687. def __init__(self, parent, host, pluginId):
  688. AbstractPluginSlot.__init__(self, parent, host, pluginId)
  689. self.ui = ui_carla_plugin_basic_fx.Ui_PluginWidget()
  690. self.ui.setupUi(self)
  691. # -------------------------------------------------------------
  692. # Set-up GUI
  693. labelFont = self.ui.label_name.font()
  694. labelFont.setBold(True)
  695. labelFont.setPointSize(9)
  696. self.ui.label_name.setFont(labelFont)
  697. r = 40
  698. g = 40
  699. b = 40
  700. if self.fPluginInfo['category'] == PLUGIN_CATEGORY_MODULATOR:
  701. r += 10
  702. elif self.fPluginInfo['category'] == PLUGIN_CATEGORY_EQ:
  703. g += 10
  704. elif self.fPluginInfo['category'] == PLUGIN_CATEGORY_FILTER:
  705. b += 10
  706. elif self.fPluginInfo['category'] == PLUGIN_CATEGORY_DELAY:
  707. r += 15
  708. b -= 15
  709. elif self.fPluginInfo['category'] == PLUGIN_CATEGORY_DISTORTION:
  710. g += 10
  711. b += 10
  712. elif self.fPluginInfo['category'] == PLUGIN_CATEGORY_DYNAMICS:
  713. r += 10
  714. b += 10
  715. elif self.fPluginInfo['category'] == PLUGIN_CATEGORY_UTILITY:
  716. r += 10
  717. g += 10
  718. bg = "noise1"
  719. if self.fPluginInfo['maker'] in ("falkTX, Michael Gruhn", "DISTRHO") and "3bandeq" in self.fPluginInfo['label'].lower():
  720. bg = "3bandeq"
  721. self.setStyleSheet("""
  722. PluginSlot_BasicFX#PluginWidget {
  723. background-color: rgb(%i, %i, %i);
  724. background-image: url(:/bitmaps/background_%s.png);
  725. background-repeat: repeat-xy;
  726. }
  727. QLabel#label_name {
  728. color: #BBB;
  729. }
  730. """ % (r, g, b, bg))
  731. self.ui.b_enable.setPixmaps(":/bitmaps/button_off.png", ":/bitmaps/button_on.png", ":/bitmaps/button_off.png")
  732. self.ui.b_edit.setPixmaps(":/bitmaps/button_edit.png", ":/bitmaps/button_edit_down.png", ":/bitmaps/button_edit_hover.png")
  733. if self.fPluginInfo['iconName'] == "distrho":
  734. self.ui.b_gui.setPixmaps(":/bitmaps/button_distrho.png", ":/bitmaps/button_distrho_down.png", ":/bitmaps/button_distrho_hover.png")
  735. elif self.fPluginInfo['iconName'] == "file":
  736. self.ui.b_gui.setPixmaps(":/bitmaps/button_file.png", ":/bitmaps/button_file_down.png", ":/bitmaps/button_file_hover.png")
  737. else:
  738. self.ui.b_gui.setPixmaps(":/bitmaps/button_gui.png", ":/bitmaps/button_gui_down.png", ":/bitmaps/button_gui_hover.png")
  739. # -------------------------------------------------------------
  740. # Set-up parameters
  741. parameterCount = self.host.get_parameter_count(self.fPluginId)
  742. index = 0
  743. for i in range(parameterCount):
  744. if index >= 8:
  745. break
  746. paramInfo = self.host.get_parameter_info(self.fPluginId, i)
  747. paramData = self.host.get_parameter_data(self.fPluginId, i)
  748. paramRanges = self.host.get_parameter_ranges(self.fPluginId, i)
  749. if paramData['type'] != PARAMETER_INPUT:
  750. continue
  751. if paramData['hints'] & PARAMETER_IS_BOOLEAN:
  752. continue
  753. if (paramData['hints'] & PARAMETER_IS_ENABLED) == 0:
  754. continue
  755. paramName = getParameterShortName(paramInfo['name'])
  756. #if self.fPluginInfo['category'] == PLUGIN_CATEGORY_FILTER:
  757. #_r = 55 + float(i)/8*200
  758. #_g = 255 - float(i)/8*200
  759. #_b = 127 - r*2
  760. #elif self.fPluginInfo['category'] == PLUGIN_CATEGORY_DELAY:
  761. #_r = 127
  762. #_g = 55 + float(i)/8*200
  763. #_b = 255 - float(i)/8*200
  764. #elif r < b < g:
  765. #_r = 55 + float(i)/8*200
  766. #_g = 127
  767. #_b = 255 - float(i)/8*200
  768. #else:
  769. _r = 255 - float(index)/8*200
  770. _g = 55 + float(index)/8*200
  771. _b = (r-40)*4
  772. #if _r < 140: _r = 140
  773. #if _g < 140: _g = 140
  774. #if _b < 140: _b = 140
  775. widget = PixmapDial(self, i)
  776. widget.setPixmap(3)
  777. widget.setLabel(paramName)
  778. widget.setCustomPaintColor(QColor(_r, _g, _b))
  779. widget.setCustomPaintMode(PixmapDial.CUSTOM_PAINT_MODE_COLOR)
  780. widget.forceWhiteLabelGradientText()
  781. widget.setMinimum(paramRanges['min'])
  782. widget.setMaximum(paramRanges['max'])
  783. if (paramData['hints'] & PARAMETER_IS_ENABLED) == 0:
  784. widget.setEnabled(False)
  785. self.ui.w_knobs.layout().insertWidget(index, widget)
  786. index += 1
  787. self.fParameterList.append([i, widget])
  788. self.ui.dial_drywet.setIndex(PARAMETER_DRYWET)
  789. self.ui.dial_drywet.setPixmap(3)
  790. self.ui.dial_drywet.setLabel("Dry/Wet")
  791. self.ui.dial_drywet.setCustomPaintMode(PixmapDial.CUSTOM_PAINT_MODE_CARLA_WET)
  792. self.ui.dial_drywet.setMinimum(0.0)
  793. self.ui.dial_drywet.setMaximum(1.0)
  794. self.ui.dial_drywet.forceWhiteLabelGradientText()
  795. self.ui.dial_drywet.setVisible(self.fPluginInfo['hints'] & PLUGIN_CAN_DRYWET)
  796. self.ui.dial_vol.setIndex(PARAMETER_VOLUME)
  797. self.ui.dial_vol.setPixmap(3)
  798. self.ui.dial_vol.setLabel("Volume")
  799. self.ui.dial_vol.setCustomPaintMode(PixmapDial.CUSTOM_PAINT_MODE_CARLA_VOL)
  800. self.ui.dial_vol.setMinimum(0.0)
  801. self.ui.dial_vol.setMaximum(1.27)
  802. self.ui.dial_vol.forceWhiteLabelGradientText()
  803. self.ui.dial_vol.setVisible(self.fPluginInfo['hints'] & PLUGIN_CAN_VOLUME)
  804. self.fParameterList.append([PARAMETER_DRYWET, self.ui.dial_drywet])
  805. self.fParameterList.append([PARAMETER_VOLUME, self.ui.dial_vol])
  806. # -------------------------------------------------------------
  807. self.b_enable = self.ui.b_enable
  808. self.b_gui = self.ui.b_gui
  809. self.b_edit = self.ui.b_edit
  810. self.label_name = self.ui.label_name
  811. self.led_control = self.ui.led_control
  812. self.led_midi = self.ui.led_midi
  813. self.led_audio_in = self.ui.led_audio_in
  814. self.led_audio_out = self.ui.led_audio_out
  815. self.peak_in = self.ui.peak_in
  816. self.peak_out = self.ui.peak_out
  817. self.ready()
  818. self.customContextMenuRequested.connect(self.slot_showDefaultCustomMenu)
  819. #------------------------------------------------------------------
  820. def getFixedHeight(self):
  821. return 79
  822. #------------------------------------------------------------------
  823. def paintEvent(self, event):
  824. painter = QPainter(self)
  825. painter.setBrush(Qt.transparent)
  826. painter.setPen(QPen(QColor(42, 42, 42), 1))
  827. painter.drawRect(0, 1, self.width()-1, 79-3)
  828. painter.setPen(QPen(QColor(60, 60, 60), 1))
  829. painter.drawLine(0, 0, self.width(), 0)
  830. AbstractPluginSlot.paintEvent(self, event)
  831. # ------------------------------------------------------------------------------------------------------------
  832. class PluginSlot_Calf(AbstractPluginSlot):
  833. def __init__(self, parent, host, pluginId):
  834. AbstractPluginSlot.__init__(self, parent, host, pluginId)
  835. self.ui = ui_carla_plugin_calf.Ui_PluginWidget()
  836. self.ui.setupUi(self)
  837. audioCount = self.host.get_audio_port_count_info(self.fPluginId)
  838. midiCount = self.host.get_midi_port_count_info(self.fPluginId)
  839. # -------------------------------------------------------------
  840. # Internal stuff
  841. self.fButtonFont = self.ui.b_gui.font()
  842. self.fButtonFont.setBold(False)
  843. self.fButtonFont.setPointSize(8)
  844. # Use black for mono plugins
  845. self.fBackgroundBlack = audioCount['ins'] == 1
  846. self.fButtonColorOn = QColor( 18, 41, 87)
  847. self.fButtonColorOff = QColor(150, 150, 150)
  848. # -------------------------------------------------------------
  849. # Set-up GUI
  850. self.setStyleSheet("""
  851. QLabel#label_name, QLabel#label_audio_in, QLabel#label_audio_out, QLabel#label_midi {
  852. color: #BBB;
  853. }
  854. PluginSlot_Calf#PluginWidget {
  855. background-image: url(:/bitmaps/background_calf_%s.png);
  856. background-repeat: repeat-xy;
  857. border: 2px;
  858. }
  859. """ % ("black" if self.fBackgroundBlack else "blue"))
  860. self.ui.b_gui.setPixmaps(":/bitmaps/button_calf2.png", ":/bitmaps/button_calf2_down.png", ":/bitmaps/button_calf2_hover.png")
  861. self.ui.b_edit.setPixmaps(":/bitmaps/button_calf2.png", ":/bitmaps/button_calf2_down.png", ":/bitmaps/button_calf2_hover.png")
  862. self.ui.b_remove.setPixmaps(":/bitmaps/button_calf1.png", ":/bitmaps/button_calf1_down.png", ":/bitmaps/button_calf1_hover.png")
  863. self.ui.b_edit.setTopText(self.tr("Edit"), self.fButtonColorOn, self.fButtonFont)
  864. self.ui.b_remove.setTopText(self.tr("Remove"), self.fButtonColorOn, self.fButtonFont)
  865. if self.fPluginInfo['hints'] & PLUGIN_HAS_CUSTOM_UI:
  866. self.ui.b_gui.setTopText(self.tr("GUI"), self.fButtonColorOn, self.fButtonFont)
  867. else:
  868. self.ui.b_gui.setTopText(self.tr("GUI"), self.fButtonColorOff, self.fButtonFont)
  869. labelFont = self.ui.label_name.font()
  870. labelFont.setBold(True)
  871. labelFont.setPointSize(10)
  872. self.ui.label_name.setFont(labelFont)
  873. if audioCount['ins'] == 0:
  874. self.ui.label_audio_in.hide()
  875. self.ui.peak_in.hide()
  876. if audioCount['outs'] > 0:
  877. self.ui.peak_out.setMinimumWidth(200)
  878. if audioCount['outs'] == 0:
  879. self.ui.label_audio_out.hide()
  880. self.ui.peak_out.hide()
  881. if midiCount['ins'] == 0:
  882. self.ui.label_midi.hide()
  883. self.ui.led_midi.hide()
  884. if self.fIdleTimerId != 0:
  885. self.ui.b_remove.setEnabled(False)
  886. self.ui.b_remove.setVisible(False)
  887. # -------------------------------------------------------------
  888. # Set-up parameters
  889. parameterCount = self.host.get_parameter_count(self.fPluginId)
  890. index = 0
  891. limit = 7 if midiCount['ins'] == 0 else 6
  892. for i in range(parameterCount):
  893. if index >= limit:
  894. break
  895. paramInfo = self.host.get_parameter_info(self.fPluginId, i)
  896. paramData = self.host.get_parameter_data(self.fPluginId, i)
  897. paramRanges = self.host.get_parameter_ranges(self.fPluginId, i)
  898. if paramData['type'] != PARAMETER_INPUT:
  899. continue
  900. if paramData['hints'] & PARAMETER_IS_BOOLEAN:
  901. continue
  902. if (paramData['hints'] & PARAMETER_IS_ENABLED) == 0:
  903. continue
  904. paramName = getParameterShortName(paramInfo['name'])
  905. widget = PixmapDial(self, i)
  906. widget.setPixmap(7)
  907. widget.setLabel(paramName)
  908. widget.setCustomPaintMode(PixmapDial.CUSTOM_PAINT_MODE_NO_GRADIENT)
  909. widget.setMinimum(paramRanges['min'])
  910. widget.setMaximum(paramRanges['max'])
  911. if (paramData['hints'] & PARAMETER_IS_ENABLED) == 0:
  912. widget.setEnabled(False)
  913. self.ui.w_knobs.layout().insertWidget(index, widget)
  914. index += 1
  915. self.fParameterList.append([i, widget])
  916. # -------------------------------------------------------------
  917. self.b_gui = self.ui.b_gui
  918. self.b_edit = self.ui.b_edit
  919. self.b_remove = self.ui.b_remove
  920. self.label_name = self.ui.label_name
  921. self.led_midi = self.ui.led_midi
  922. self.peak_in = self.ui.peak_in
  923. self.peak_out = self.ui.peak_out
  924. self.ready()
  925. self.ui.led_midi.setColor(self.ui.led_midi.CALF)
  926. self.customContextMenuRequested.connect(self.slot_showDefaultCustomMenu)
  927. #------------------------------------------------------------------
  928. def getFixedHeight(self):
  929. return 88
  930. #------------------------------------------------------------------
  931. def editDialogPluginHintsChanged(self, pluginId, hints):
  932. if hints & PLUGIN_HAS_CUSTOM_UI:
  933. self.ui.b_gui.setTopText(self.tr("GUI"), self.fButtonColorOn, self.fButtonFont)
  934. else:
  935. self.ui.b_gui.setTopText(self.tr("GUI"), self.fButtonColorOff, self.fButtonFont)
  936. AbstractPluginSlot.editDialogPluginHintsChanged(self, pluginId, hints)
  937. #------------------------------------------------------------------
  938. def paintEvent(self, event):
  939. painter = QPainter(self)
  940. painter.setBrush(Qt.transparent)
  941. painter.setPen(QPen(QColor(20, 20, 20) if self.fBackgroundBlack else QColor(75, 86, 99), 1))
  942. painter.drawRect(0, 1, self.width()-1, 88-3)
  943. painter.setPen(QPen(QColor(45, 45, 45) if self.fBackgroundBlack else QColor(86, 99, 114), 1))
  944. painter.drawLine(0, 0, self.width(), 0)
  945. AbstractPluginSlot.paintEvent(self, event)
  946. # ------------------------------------------------------------------------------------------------------------
  947. class PluginSlot_OpenAV(AbstractPluginSlot):
  948. def __init__(self, parent, host, pluginId):
  949. AbstractPluginSlot.__init__(self, parent, host, pluginId)
  950. self.ui = ui_carla_plugin_basic_fx.Ui_PluginWidget()
  951. self.ui.setupUi(self)
  952. # -------------------------------------------------------------
  953. # Set-up GUI
  954. QFontDatabase.addApplicationFont(":/fonts/uranium.ttf")
  955. labelFont = QFont()
  956. labelFont.setFamily("Uranium")
  957. labelFont.setPointSize(13)
  958. labelFont.setCapitalization(QFont.AllUppercase)
  959. self.ui.label_name.setFont(labelFont)
  960. self.setStyleSheet("""
  961. PluginSlot_OpenAV#PluginWidget {
  962. background-color: qlineargradient(x1: 0, y1: 0, x2: 0, y2: 1,
  963. stop: 0 #303030, stop: 0.35 #111111, stop: 1.0 #111111);
  964. }
  965. """)
  966. self.ui.label_name.setStyleSheet("* { color: #FF5100; }")
  967. #self.ui.line.setStyleSheet("* { background-color: #FF5100; color: #FF5100; }")
  968. self.ui.peak_in.setMeterStyle(DigitalPeakMeter.STYLE_OPENAV)
  969. self.ui.peak_out.setMeterStyle(DigitalPeakMeter.STYLE_OPENAV)
  970. self.ui.b_enable.setPixmaps(":/bitmaps/button_off.png", ":/bitmaps/button_on.png", ":/bitmaps/button_off.png")
  971. self.ui.b_edit.setPixmaps(":/bitmaps/button_edit.png", ":/bitmaps/button_edit_down.png", ":/bitmaps/button_edit_hover.png")
  972. self.ui.b_gui.setPixmaps(":/bitmaps/button_gui.png", ":/bitmaps/button_gui_down.png", ":/bitmaps/button_gui_hover.png")
  973. # -------------------------------------------------------------
  974. # Set-up parameters
  975. parameterCount = self.host.get_parameter_count(self.fPluginId)
  976. index = 0
  977. for i in range(parameterCount):
  978. if index >= 8:
  979. break
  980. paramInfo = self.host.get_parameter_info(self.fPluginId, i)
  981. paramData = self.host.get_parameter_data(self.fPluginId, i)
  982. paramRanges = self.host.get_parameter_ranges(self.fPluginId, i)
  983. if paramData['type'] != PARAMETER_INPUT:
  984. continue
  985. if paramData['hints'] & PARAMETER_IS_BOOLEAN:
  986. continue
  987. if (paramData['hints'] & PARAMETER_IS_ENABLED) == 0:
  988. continue
  989. paramName = getParameterShortName(paramInfo['name'])
  990. widget = PixmapDial(self, i)
  991. widget.setPixmap(11)
  992. widget.setLabel(paramName)
  993. widget.setCustomPaintMode(PixmapDial.CUSTOM_PAINT_MODE_NO_GRADIENT)
  994. widget.setMinimum(paramRanges['min'])
  995. widget.setMaximum(paramRanges['max'])
  996. if (paramData['hints'] & PARAMETER_IS_ENABLED) == 0:
  997. widget.setEnabled(False)
  998. self.ui.w_knobs.layout().insertWidget(index, widget)
  999. index += 1
  1000. self.fParameterList.append([i, widget])
  1001. self.ui.dial_drywet.setIndex(PARAMETER_DRYWET)
  1002. self.ui.dial_drywet.setPixmap(13)
  1003. self.ui.dial_drywet.setLabel("Dry/Wet")
  1004. self.ui.dial_drywet.setCustomPaintMode(PixmapDial.CUSTOM_PAINT_MODE_NO_GRADIENT)
  1005. self.ui.dial_drywet.setMinimum(0.0)
  1006. self.ui.dial_drywet.setMaximum(1.0)
  1007. self.ui.dial_drywet.setVisible(self.fPluginInfo['hints'] & PLUGIN_CAN_DRYWET)
  1008. self.ui.dial_vol.setIndex(PARAMETER_VOLUME)
  1009. self.ui.dial_vol.setPixmap(12)
  1010. self.ui.dial_vol.setLabel("Volume")
  1011. self.ui.dial_vol.setCustomPaintMode(PixmapDial.CUSTOM_PAINT_MODE_NO_GRADIENT)
  1012. self.ui.dial_vol.setMinimum(0.0)
  1013. self.ui.dial_vol.setMaximum(1.27)
  1014. self.ui.dial_vol.setVisible(self.fPluginInfo['hints'] & PLUGIN_CAN_VOLUME)
  1015. self.fParameterList.append([PARAMETER_DRYWET, self.ui.dial_drywet])
  1016. self.fParameterList.append([PARAMETER_VOLUME, self.ui.dial_vol])
  1017. # -------------------------------------------------------------
  1018. self.b_enable = self.ui.b_enable
  1019. self.b_gui = self.ui.b_gui
  1020. self.b_edit = self.ui.b_edit
  1021. self.label_name = self.ui.label_name
  1022. self.led_control = self.ui.led_control
  1023. self.led_midi = self.ui.led_midi
  1024. self.led_audio_in = self.ui.led_audio_in
  1025. self.led_audio_out = self.ui.led_audio_out
  1026. self.peak_in = self.ui.peak_in
  1027. self.peak_out = self.ui.peak_out
  1028. self.ready()
  1029. self.customContextMenuRequested.connect(self.slot_showDefaultCustomMenu)
  1030. #------------------------------------------------------------------
  1031. def getFixedHeight(self):
  1032. return 79
  1033. #------------------------------------------------------------------
  1034. def paintEvent(self, event):
  1035. painter = QPainter(self)
  1036. painter.setBrush(Qt.transparent)
  1037. painter.setPen(QPen(QColor(42, 42, 42), 1))
  1038. painter.drawRect(0, 1, self.width()-1, 79-3)
  1039. painter.setPen(QPen(QColor(60, 60, 60), 1))
  1040. painter.drawLine(0, 0, self.width(), 0)
  1041. AbstractPluginSlot.paintEvent(self, event)
  1042. # ------------------------------------------------------------------------------------------------------------
  1043. class PluginSlot_Nekobi(AbstractPluginSlot):
  1044. def __init__(self, parent, host, pluginId):
  1045. AbstractPluginSlot.__init__(self, parent, host, pluginId)
  1046. #self.ui = ui_carla_plugin_basic_fx.Ui_PluginWidget()
  1047. #self.ui.setupUi(self)
  1048. # -------------------------------------------------------------
  1049. # Set-up GUI
  1050. self.fPixmapCenter = QPixmap(":/bitmaps/background_nekobi.png")
  1051. self.fPixmapLeft = QPixmap(":/bitmaps/background_nekobi_left.png")
  1052. self.fPixmapLeftRect = QRectF(0, 0, self.fPixmapLeft.width(), self.fPixmapLeft.height())
  1053. self.fPixmapRight = QPixmap(":/bitmaps/background_nekobi_right.png")
  1054. self.fPixmapRightRect = QRectF(0, 0, self.fPixmapRight.width(), self.fPixmapRight.height())
  1055. #self.setStyleSheet("""
  1056. #PluginSlot_Nekobi#PluginWidget {
  1057. #background-image: url(:/bitmaps/background_nekobi.png);
  1058. #background-repeat: repeat-xy;
  1059. #}
  1060. #QLabel#label_name {
  1061. #color: #BBB;
  1062. #}
  1063. #""")
  1064. #------------------------------------------------------------------
  1065. def getFixedHeight(self):
  1066. return 108
  1067. #------------------------------------------------------------------
  1068. def paintEvent(self, event):
  1069. painter = QPainter(self)
  1070. # main bg (center)
  1071. painter.drawTiledPixmap(0, 0, self.width(), self.height(), self.fPixmapCenter)
  1072. # left side
  1073. painter.drawPixmap(self.fPixmapLeftRect, self.fPixmapLeft, self.fPixmapLeftRect)
  1074. # right side
  1075. rightTarget = QRectF(self.fPixmapRightRect)
  1076. rightTarget.moveLeft(self.width()-rightTarget.width())
  1077. painter.drawPixmap(rightTarget, self.fPixmapRight, self.fPixmapRightRect)
  1078. AbstractPluginSlot.paintEvent(self, event)
  1079. # ------------------------------------------------------------------------------------------------------------
  1080. class PluginSlot_SF2(AbstractPluginSlot):
  1081. def __init__(self, parent, host, pluginId):
  1082. AbstractPluginSlot.__init__(self, parent, host, pluginId)
  1083. self.ui = ui_carla_plugin_sf2.Ui_PluginWidget()
  1084. self.ui.setupUi(self)
  1085. # -------------------------------------------------------------
  1086. # Set-up GUI
  1087. #labelFont = self.ui.label_name.font()
  1088. #labelFont.setBold(True)
  1089. #labelFont.setPointSize(9)
  1090. #self.ui.label_name.setFont(labelFont)
  1091. self.setStyleSheet("""
  1092. PluginSlot_SF2#PluginWidget {
  1093. background-image: url(:/bitmaps/background_3bandeq.png);
  1094. background-repeat: repeat-xy;
  1095. }
  1096. QLabel#label_name {
  1097. color: #BBB;
  1098. }
  1099. """)
  1100. self.ui.b_enable.setPixmaps(":/bitmaps/button_off.png", ":/bitmaps/button_on.png", ":/bitmaps/button_off.png")
  1101. self.ui.b_edit.setPixmaps(":/bitmaps/button_edit.png", ":/bitmaps/button_edit_down.png", ":/bitmaps/button_edit_hover.png")
  1102. # -------------------------------------------------------------
  1103. # Set-up parameters
  1104. parameterCount = self.host.get_parameter_count(self.fPluginId)
  1105. index = 0
  1106. for i in range(parameterCount):
  1107. if index >= 8:
  1108. break
  1109. paramInfo = self.host.get_parameter_info(self.fPluginId, i)
  1110. paramData = self.host.get_parameter_data(self.fPluginId, i)
  1111. paramRanges = self.host.get_parameter_ranges(self.fPluginId, i)
  1112. if paramData['type'] != PARAMETER_INPUT:
  1113. continue
  1114. if paramData['hints'] & PARAMETER_IS_BOOLEAN:
  1115. continue
  1116. if (paramData['hints'] & PARAMETER_IS_ENABLED) == 0:
  1117. continue
  1118. paramName = getParameterShortName(paramInfo['name'])
  1119. widget = PixmapDial(self, i)
  1120. widget.setPixmap(3)
  1121. widget.setLabel(paramName)
  1122. widget.setMinimum(paramRanges['min'])
  1123. widget.setMaximum(paramRanges['max'])
  1124. if (paramData['hints'] & PARAMETER_IS_ENABLED) == 0:
  1125. widget.setEnabled(False)
  1126. self.ui.w_knobs.layout().insertWidget(index, widget)
  1127. index += 1
  1128. self.fParameterList.append([i, widget])
  1129. self.ui.dial_vol.setIndex(PARAMETER_VOLUME)
  1130. self.ui.dial_vol.setPixmap(3)
  1131. self.ui.dial_vol.setLabel("Volume")
  1132. self.ui.dial_vol.setCustomPaintMode(PixmapDial.CUSTOM_PAINT_MODE_CARLA_VOL)
  1133. self.ui.dial_vol.setMinimum(0.0)
  1134. self.ui.dial_vol.setMaximum(1.27)
  1135. self.ui.dial_vol.forceWhiteLabelGradientText()
  1136. self.ui.dial_vol.setVisible(self.fPluginInfo['hints'] & PLUGIN_CAN_VOLUME)
  1137. self.fParameterList.append([PARAMETER_VOLUME, self.ui.dial_vol])
  1138. # -------------------------------------------------------------
  1139. self.b_enable = self.ui.b_enable
  1140. self.b_edit = self.ui.b_edit
  1141. self.label_name = self.ui.label_name
  1142. self.led_control = self.ui.led_control
  1143. self.led_midi = self.ui.led_midi
  1144. self.led_audio_out = self.ui.led_audio_out
  1145. self.peak_out = self.ui.peak_out
  1146. self.ready()
  1147. self.customContextMenuRequested.connect(self.slot_showDefaultCustomMenu)
  1148. #------------------------------------------------------------------
  1149. def getFixedHeight(self):
  1150. return 79
  1151. #------------------------------------------------------------------
  1152. def paintEvent(self, event):
  1153. painter = QPainter(self)
  1154. painter.setBrush(Qt.transparent)
  1155. painter.setPen(QPen(QColor(42, 42, 42), 1))
  1156. painter.drawRect(0, 1, self.width()-1, 79-3)
  1157. painter.setPen(QPen(QColor(60, 60, 60), 1))
  1158. painter.drawLine(0, 0, self.width(), 0)
  1159. AbstractPluginSlot.paintEvent(self, event)
  1160. # ------------------------------------------------------------------------------------------------------------
  1161. class PluginSlot_ZitaRev(AbstractPluginSlot):
  1162. def __init__(self, parent, host, pluginId):
  1163. AbstractPluginSlot.__init__(self, parent, host, pluginId)
  1164. self.ui = ui_carla_plugin_zita.Ui_PluginWidget()
  1165. self.ui.setupUi(self)
  1166. # -------------------------------------------------------------
  1167. # Internal stuff
  1168. audioCount = self.host.get_audio_port_count_info(self.fPluginId)
  1169. # -------------------------------------------------------------
  1170. # Set-up GUI
  1171. self.setMinimumWidth(640)
  1172. self.setStyleSheet("""
  1173. PluginSlot_ZitaRev#PluginWidget {
  1174. background-color: #404040;
  1175. border: 2px solid transparent;
  1176. }
  1177. QWidget#w_revsect {
  1178. background-image: url(:/bitmaps/zita-rev/revsect.png);
  1179. }
  1180. QWidget#w_eq1sect {
  1181. background-image: url(:/bitmaps/zita-rev/eq1sect.png);
  1182. }
  1183. QWidget#w_eq2sect {
  1184. background-image: url(:/bitmaps/zita-rev/eq2sect.png);
  1185. }
  1186. QWidget#w_ambmixsect {
  1187. background-image: url(:/bitmaps/zita-rev/%s.png);
  1188. }
  1189. QWidget#w_redzita {
  1190. background-image: url(:/bitmaps/zita-rev/redzita.png);
  1191. }
  1192. """ % ("mixsect" if audioCount['outs'] == 2 else "ambsect"))
  1193. # -------------------------------------------------------------
  1194. # Set-up Knobs
  1195. self.fKnobDelay = PixmapDial(self, 0)
  1196. self.fKnobDelay.setPixmap(6)
  1197. self.fKnobDelay.setCustomPaintMode(PixmapDial.CUSTOM_PAINT_MODE_ZITA)
  1198. self.fKnobDelay.setMinimum(0.02)
  1199. self.fKnobDelay.setMaximum(0.10)
  1200. self.fKnobXover = PixmapDial(self, 1)
  1201. self.fKnobXover.setPixmap(6)
  1202. self.fKnobXover.setCustomPaintMode(PixmapDial.CUSTOM_PAINT_MODE_ZITA)
  1203. self.fKnobXover.setMinimum(50.0)
  1204. self.fKnobXover.setMaximum(1000.0)
  1205. self.fKnobRtLow = PixmapDial(self, 2)
  1206. self.fKnobRtLow.setPixmap(6)
  1207. self.fKnobRtLow.setCustomPaintMode(PixmapDial.CUSTOM_PAINT_MODE_ZITA)
  1208. self.fKnobRtLow.setMinimum(1.0)
  1209. self.fKnobRtLow.setMaximum(8.0)
  1210. self.fKnobRtMid = PixmapDial(self, 3)
  1211. self.fKnobRtMid.setPixmap(6)
  1212. self.fKnobRtMid.setCustomPaintMode(PixmapDial.CUSTOM_PAINT_MODE_ZITA)
  1213. self.fKnobRtMid.setMinimum(1.0)
  1214. self.fKnobRtMid.setMaximum(8.0)
  1215. self.fKnobDamping = PixmapDial(self, 4)
  1216. self.fKnobDamping.setPixmap(6)
  1217. self.fKnobDamping.setCustomPaintMode(PixmapDial.CUSTOM_PAINT_MODE_ZITA)
  1218. self.fKnobDamping.setMinimum(1500.0)
  1219. self.fKnobDamping.setMaximum(24000.0)
  1220. self.fKnobEq1Freq = PixmapDial(self, 5)
  1221. self.fKnobEq1Freq.setPixmap(6)
  1222. self.fKnobEq1Freq.setCustomPaintMode(PixmapDial.CUSTOM_PAINT_MODE_ZITA)
  1223. self.fKnobEq1Freq.setMinimum(40.0)
  1224. self.fKnobEq1Freq.setMaximum(10000.0)
  1225. self.fKnobEq1Gain = PixmapDial(self, 6)
  1226. self.fKnobEq1Gain.setPixmap(6)
  1227. self.fKnobEq1Gain.setCustomPaintMode(PixmapDial.CUSTOM_PAINT_MODE_ZITA)
  1228. self.fKnobEq1Gain.setMinimum(-20.0)
  1229. self.fKnobEq1Gain.setMaximum(20.0)
  1230. self.fKnobEq2Freq = PixmapDial(self, 7)
  1231. self.fKnobEq2Freq.setPixmap(6)
  1232. self.fKnobEq2Freq.setCustomPaintMode(PixmapDial.CUSTOM_PAINT_MODE_ZITA)
  1233. self.fKnobEq2Freq.setMinimum(40.0)
  1234. self.fKnobEq2Freq.setMaximum(10000.0)
  1235. self.fKnobEq2Gain = PixmapDial(self, 8)
  1236. self.fKnobEq2Gain.setPixmap(6)
  1237. self.fKnobEq2Gain.setCustomPaintMode(PixmapDial.CUSTOM_PAINT_MODE_ZITA)
  1238. self.fKnobEq2Gain.setMinimum(-20.0)
  1239. self.fKnobEq2Gain.setMaximum(20.0)
  1240. self.fKnobMix = PixmapDial(self, 9)
  1241. self.fKnobMix.setPixmap(6)
  1242. self.fKnobMix.setCustomPaintMode(PixmapDial.CUSTOM_PAINT_MODE_ZITA)
  1243. self.fKnobMix.setMinimum(0.0)
  1244. self.fKnobMix.setMaximum(1.0)
  1245. self.fParameterList.append([0, self.fKnobDelay])
  1246. self.fParameterList.append([1, self.fKnobXover])
  1247. self.fParameterList.append([2, self.fKnobRtLow])
  1248. self.fParameterList.append([3, self.fKnobRtMid])
  1249. self.fParameterList.append([4, self.fKnobDamping])
  1250. self.fParameterList.append([5, self.fKnobEq1Freq])
  1251. self.fParameterList.append([6, self.fKnobEq1Gain])
  1252. self.fParameterList.append([7, self.fKnobEq2Freq])
  1253. self.fParameterList.append([8, self.fKnobEq2Gain])
  1254. self.fParameterList.append([9, self.fKnobMix])
  1255. # -------------------------------------------------------------
  1256. self.ready()
  1257. self.customContextMenuRequested.connect(self.slot_showDefaultCustomMenu)
  1258. #------------------------------------------------------------------
  1259. def getFixedHeight(self):
  1260. return 79
  1261. #------------------------------------------------------------------
  1262. def paintEvent(self, event):
  1263. AbstractPluginSlot.paintEvent(self, event)
  1264. self.drawOutline()
  1265. def resizeEvent(self, event):
  1266. self.fKnobDelay.move(self.ui.w_revsect.x()+31, self.ui.w_revsect.y()+33)
  1267. self.fKnobXover.move(self.ui.w_revsect.x()+93, self.ui.w_revsect.y()+18)
  1268. self.fKnobRtLow.move(self.ui.w_revsect.x()+148, self.ui.w_revsect.y()+18)
  1269. self.fKnobRtMid.move(self.ui.w_revsect.x()+208, self.ui.w_revsect.y()+18)
  1270. self.fKnobDamping.move(self.ui.w_revsect.x()+268, self.ui.w_revsect.y()+18)
  1271. self.fKnobEq1Freq.move(self.ui.w_eq1sect.x()+20, self.ui.w_eq1sect.y()+33)
  1272. self.fKnobEq1Gain.move(self.ui.w_eq1sect.x()+69, self.ui.w_eq1sect.y()+18)
  1273. self.fKnobEq2Freq.move(self.ui.w_eq2sect.x()+20, self.ui.w_eq2sect.y()+33)
  1274. self.fKnobEq2Gain.move(self.ui.w_eq2sect.x()+69, self.ui.w_eq2sect.y()+18)
  1275. self.fKnobMix.move(self.ui.w_ambmixsect.x()+24, self.ui.w_ambmixsect.y()+33)
  1276. AbstractPluginSlot.resizeEvent(self, event)
  1277. # ------------------------------------------------------------------------------------------------------------
  1278. class PluginSlot_ZynFX(AbstractPluginSlot):
  1279. def __init__(self, parent, host, pluginId):
  1280. AbstractPluginSlot.__init__(self, parent, host, pluginId)
  1281. self.ui = ui_carla_plugin_zynfx.Ui_PluginWidget()
  1282. self.ui.setupUi(self)
  1283. # -------------------------------------------------------------
  1284. # Set-up GUI
  1285. self.setStyleSheet("""
  1286. PluginSlot_ZynFX#PluginWidget {
  1287. background-image: url(:/bitmaps/background_zynfx.png);
  1288. background-repeat: repeat-xy;
  1289. border: 2px;
  1290. }
  1291. QLabel#label_name, QLabel#label_presets {
  1292. color: #BBB;
  1293. }
  1294. """)
  1295. self.ui.b_enable.setPixmaps(":/bitmaps/button_off.png", ":/bitmaps/button_on.png", ":/bitmaps/button_off.png")
  1296. self.ui.b_edit.setPixmaps(":/bitmaps/button_edit.png", ":/bitmaps/button_edit_down.png", ":/bitmaps/button_edit_hover.png")
  1297. labelFont = self.ui.label_name.font()
  1298. labelFont.setBold(True)
  1299. labelFont.setPointSize(9)
  1300. self.ui.label_name.setFont(labelFont)
  1301. presetFont = self.ui.label_presets.font()
  1302. presetFont.setBold(True)
  1303. presetFont.setPointSize(8)
  1304. self.ui.label_presets.setFont(presetFont)
  1305. self.ui.peak_in.setMeterStyle(DigitalPeakMeter.STYLE_OPENAV)
  1306. self.ui.peak_out.setMeterStyle(DigitalPeakMeter.STYLE_OPENAV)
  1307. # -------------------------------------------------------------
  1308. # Set-up parameters
  1309. parameterCount = self.host.get_parameter_count(self.fPluginId)
  1310. index = 0
  1311. for i in range(parameterCount):
  1312. paramInfo = self.host.get_parameter_info(self.fPluginId, i)
  1313. paramData = self.host.get_parameter_data(self.fPluginId, i)
  1314. paramRanges = self.host.get_parameter_ranges(self.fPluginId, i)
  1315. if paramData['type'] != PARAMETER_INPUT:
  1316. continue
  1317. if paramData['hints'] & PARAMETER_IS_BOOLEAN:
  1318. continue
  1319. if (paramData['hints'] & PARAMETER_IS_ENABLED) == 0:
  1320. continue
  1321. paramName = paramInfo['name']
  1322. # real zyn fx plugins
  1323. if self.fPluginInfo['label'] == "zynalienwah":
  1324. if i == 0: paramName = "Freq"
  1325. elif i == 1: paramName = "Rnd"
  1326. elif i == 2: paramName = "L type" # combobox
  1327. elif i == 3: paramName = "St.df"
  1328. elif i == 5: paramName = "Fb"
  1329. elif i == 7: paramName = "L/R"
  1330. elif self.fPluginInfo['label'] == "zynchorus":
  1331. if i == 0: paramName = "Freq"
  1332. elif i == 1: paramName = "Rnd"
  1333. elif i == 2: paramName = "L type" # combobox
  1334. elif i == 3: paramName = "St.df"
  1335. elif i == 6: paramName = "Fb"
  1336. elif i == 7: paramName = "L/R"
  1337. elif i == 8: paramName = "Flngr" # button
  1338. elif i == 9: paramName = "Subst" # button
  1339. elif self.fPluginInfo['label'] == "zyndistortion":
  1340. if i == 0: paramName = "LRc."
  1341. elif i == 4: paramName = "Neg." # button
  1342. elif i == 5: paramName = "LPF"
  1343. elif i == 6: paramName = "HPF"
  1344. elif i == 7: paramName = "St." # button
  1345. elif i == 8: paramName = "PF" # button
  1346. elif self.fPluginInfo['label'] == "zyndynamicfilter":
  1347. if i == 0: paramName = "Freq"
  1348. elif i == 1: paramName = "Rnd"
  1349. elif i == 2: paramName = "L type" # combobox
  1350. elif i == 3: paramName = "St.df"
  1351. elif i == 4: paramName = "LfoD"
  1352. elif i == 5: paramName = "A.S."
  1353. elif i == 6: paramName = "A.Inv." # button
  1354. elif i == 7: paramName = "A.M."
  1355. elif self.fPluginInfo['label'] == "zynecho":
  1356. if i == 1: paramName = "LRdl."
  1357. elif i == 2: paramName = "LRc."
  1358. elif i == 3: paramName = "Fb."
  1359. elif i == 4: paramName = "Damp"
  1360. elif self.fPluginInfo['label'] == "zynphaser":
  1361. if i == 0: paramName = "Freq"
  1362. elif i == 1: paramName = "Rnd"
  1363. elif i == 2: paramName = "L type" # combobox
  1364. elif i == 3: paramName = "St.df"
  1365. elif i == 5: paramName = "Fb"
  1366. elif i == 7: paramName = "L/R"
  1367. elif i == 8: paramName = "Subst" # button
  1368. elif i == 9: paramName = "Phase"
  1369. elif i == 11: paramName = "Dist"
  1370. elif self.fPluginInfo['label'] == "zynreverb":
  1371. if i == 2: paramName = "I.delfb"
  1372. elif i == 5: paramName = "LPF"
  1373. elif i == 6: paramName = "HPF"
  1374. elif i == 9: paramName = "R.S."
  1375. elif i == 10: paramName = "I.del"
  1376. else:
  1377. paramName = getParameterShortName(paramInfo['name'])
  1378. widget = PixmapDial(self, i)
  1379. widget.setPixmap(5)
  1380. widget.setLabel(paramName)
  1381. widget.setCustomPaintMode(PixmapDial.CUSTOM_PAINT_MODE_NO_GRADIENT)
  1382. widget.setMinimum(paramRanges['min'])
  1383. widget.setMaximum(paramRanges['max'])
  1384. if (paramData['hints'] & PARAMETER_IS_ENABLED) == 0:
  1385. widget.setEnabled(False)
  1386. self.ui.w_knobs.layout().insertWidget(index, widget)
  1387. index += 1
  1388. self.fParameterList.append([i, widget])
  1389. self.ui.dial_drywet.setIndex(PARAMETER_DRYWET)
  1390. self.ui.dial_drywet.setPixmap(5)
  1391. self.ui.dial_drywet.setLabel("Wet")
  1392. self.ui.dial_drywet.setCustomPaintMode(PixmapDial.CUSTOM_PAINT_MODE_NO_GRADIENT)
  1393. self.ui.dial_drywet.setMinimum(0.0)
  1394. self.ui.dial_drywet.setMaximum(1.0)
  1395. self.ui.dial_drywet.setVisible(self.fPluginInfo['hints'] & PLUGIN_CAN_DRYWET)
  1396. self.ui.dial_vol.setIndex(PARAMETER_VOLUME)
  1397. self.ui.dial_vol.setPixmap(5)
  1398. self.ui.dial_vol.setLabel("Vol")
  1399. self.ui.dial_vol.setCustomPaintMode(PixmapDial.CUSTOM_PAINT_MODE_NO_GRADIENT)
  1400. self.ui.dial_vol.setMinimum(0.0)
  1401. self.ui.dial_vol.setMaximum(1.27)
  1402. self.ui.dial_vol.setVisible(self.fPluginInfo['hints'] & PLUGIN_CAN_VOLUME)
  1403. self.fParameterList.append([PARAMETER_DRYWET, self.ui.dial_drywet])
  1404. self.fParameterList.append([PARAMETER_VOLUME, self.ui.dial_vol])
  1405. # -------------------------------------------------------------
  1406. # Set-up MIDI programs
  1407. midiProgramCount = self.host.get_midi_program_count(self.fPluginId)
  1408. if midiProgramCount > 0:
  1409. self.ui.cb_presets.setEnabled(True)
  1410. self.ui.label_presets.setEnabled(True)
  1411. for i in range(midiProgramCount):
  1412. mpData = self.host.get_midi_program_data(self.fPluginId, i)
  1413. mpName = mpData['name']
  1414. self.ui.cb_presets.addItem(mpName)
  1415. self.fCurrentMidiProgram = self.host.get_current_midi_program_index(self.fPluginId)
  1416. self.ui.cb_presets.setCurrentIndex(self.fCurrentMidiProgram)
  1417. else:
  1418. self.fCurrentMidiProgram = -1
  1419. self.ui.cb_presets.setEnabled(False)
  1420. self.ui.cb_presets.setVisible(False)
  1421. self.ui.label_presets.setEnabled(False)
  1422. self.ui.label_presets.setVisible(False)
  1423. # -------------------------------------------------------------
  1424. self.b_enable = self.ui.b_enable
  1425. self.b_edit = self.ui.b_edit
  1426. self.cb_presets = self.ui.cb_presets
  1427. self.label_name = self.ui.label_name
  1428. self.led_control = self.ui.led_control
  1429. self.led_midi = self.ui.led_midi
  1430. self.led_audio_in = self.ui.led_audio_in
  1431. self.led_audio_out = self.ui.led_audio_out
  1432. self.peak_in = self.ui.peak_in
  1433. self.peak_out = self.ui.peak_out
  1434. self.ready()
  1435. self.customContextMenuRequested.connect(self.slot_showDefaultCustomMenu)
  1436. self.ui.cb_presets.currentIndexChanged.connect(self.slot_midiProgramChanged)
  1437. #------------------------------------------------------------------
  1438. def getFixedHeight(self):
  1439. return 77
  1440. #------------------------------------------------------------------
  1441. def paintEvent(self, event):
  1442. painter = QPainter(self)
  1443. painter.setBrush(Qt.transparent)
  1444. painter.setPen(QPen(QColor(60, 60, 60), 1))
  1445. painter.drawRect(0, 1, self.width()-1, self.height()-3)
  1446. painter.setPen(QPen(QColor(94, 94, 94), 1))
  1447. painter.drawLine(0, 0, self.width(), 0)
  1448. AbstractPluginSlot.paintEvent(self, event)
  1449. # ------------------------------------------------------------------------------------------------------------
  1450. def createPluginSlot(parent, host, pluginId, useSkins):
  1451. if not useSkins:
  1452. return PluginSlot_Default(parent, host, pluginId)
  1453. pluginInfo = host.get_plugin_info(pluginId)
  1454. pluginName = host.get_real_plugin_name(pluginId)
  1455. pluginLabel = pluginInfo['label']
  1456. pluginMaker = pluginInfo['maker']
  1457. uniqueId = pluginInfo['uniqueId']
  1458. #pluginIcon = pluginInfo['iconName']
  1459. if pluginInfo['type'] == PLUGIN_SF2:
  1460. return PluginSlot_SF2(parent, host, pluginId)
  1461. if pluginMaker == "OpenAV Productions":
  1462. return PluginSlot_OpenAV(parent, host, pluginId)
  1463. if pluginInfo['type'] == PLUGIN_INTERNAL:
  1464. if pluginLabel.startswith("zyn") and pluginInfo['category'] != PLUGIN_CATEGORY_SYNTH:
  1465. return PluginSlot_ZynFX(parent, host, pluginId)
  1466. elif pluginInfo['type'] == PLUGIN_LADSPA:
  1467. if (pluginLabel == "zita-reverb" and uniqueId == 3701) or (pluginLabel == "zita-reverb-amb" and uniqueId == 3702):
  1468. return PluginSlot_ZitaRev(parent, host, pluginId)
  1469. if pluginLabel.startswith("Zyn") and pluginMaker.startswith("Josep Andreu"):
  1470. return PluginSlot_ZynFX(parent, host, pluginId)
  1471. if pluginName.split(" ", 1)[0].lower() == "calf":
  1472. return PluginSlot_Calf(parent, host, pluginId)
  1473. #if pluginName.lower() == "nekobi":
  1474. #return PluginSlot_Nekobi(parent, pluginId)
  1475. return PluginSlot_BasicFX(parent, host, pluginId)
  1476. # ------------------------------------------------------------------------------------------------------------
  1477. # Main Testing
  1478. if __name__ == '__main__':
  1479. from carla_app import CarlaApplication
  1480. from carla_host import initHost, loadHostSettings
  1481. import resources_rc
  1482. app = CarlaApplication("Carla-Skins")
  1483. host = initHost("Skins", None, False, False, False)
  1484. loadHostSettings(host)
  1485. host.engine_init("JACK", "Carla-Widgets")
  1486. host.add_plugin(BINARY_NATIVE, PLUGIN_INTERNAL, "", "", "zynreverb", 0, None)
  1487. #host.add_plugin(BINARY_NATIVE, PLUGIN_DSSI, "/usr/lib/dssi/karplong.so", "karplong", "karplong", 0, None)
  1488. #host.add_plugin(BINARY_NATIVE, PLUGIN_LV2, "", "", "http://www.openavproductions.com/sorcer", 0, None)
  1489. #host.add_plugin(BINARY_NATIVE, PLUGIN_LV2, "", "", "http://calf.sourceforge.net/plugins/Compressor", 0, None)
  1490. host.set_active(0, True)
  1491. gui = createPluginSlot(None, host, 0, True)
  1492. gui.testTimer()
  1493. gui.show()
  1494. app.exec_()