InstrumentTrack.h 10 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476
  1. /*
  2. * InstrumentTrack.h - declaration of class InstrumentTrack, a track + window
  3. * which holds an instrument-plugin
  4. *
  5. * Copyright (c) 2004-2014 Tobias Doerffel <tobydox/at/users.sourceforge.net>
  6. *
  7. * This file is part of LMMS - https://lmms.io
  8. *
  9. * This program is free software; you can redistribute it and/or
  10. * modify it under the terms of the GNU General Public
  11. * License as published by the Free Software Foundation; either
  12. * version 2 of the License, or (at your option) any later version.
  13. *
  14. * This program is distributed in the hope that it will be useful,
  15. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  16. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
  17. * General Public License for more details.
  18. *
  19. * You should have received a copy of the GNU General Public
  20. * License along with this program (see COPYING); if not, write to the
  21. * Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
  22. * Boston, MA 02110-1301 USA.
  23. *
  24. */
  25. #ifndef INSTRUMENT_TRACK_H
  26. #define INSTRUMENT_TRACK_H
  27. #include "AudioPort.h"
  28. #include "GroupBox.h"
  29. #include "InstrumentFunctions.h"
  30. #include "InstrumentSoundShaping.h"
  31. #include "MidiEventProcessor.h"
  32. #include "MidiPort.h"
  33. #include "NotePlayHandle.h"
  34. #include "Piano.h"
  35. #include "PianoView.h"
  36. #include "Pitch.h"
  37. #include "Plugin.h"
  38. #include "Track.h"
  39. class QLineEdit;
  40. template<class T> class QQueue;
  41. class InstrumentFunctionArpeggioView;
  42. class InstrumentFunctionNoteStackingView;
  43. class EffectRackView;
  44. class InstrumentSoundShapingView;
  45. class FadeButton;
  46. class Instrument;
  47. class InstrumentTrackWindow;
  48. class InstrumentMidiIOView;
  49. class InstrumentMiscView;
  50. class Knob;
  51. class FxLineLcdSpinBox;
  52. class LcdSpinBox;
  53. class LeftRightNav;
  54. class midiPortMenu;
  55. class DataFile;
  56. class PluginView;
  57. class TabWidget;
  58. class TrackLabelButton;
  59. class LedCheckBox;
  60. class QLabel;
  61. class LMMS_EXPORT InstrumentTrack : public Track, public MidiEventProcessor
  62. {
  63. Q_OBJECT
  64. MM_OPERATORS
  65. mapPropertyFromModel(int,getVolume,setVolume,m_volumeModel);
  66. public:
  67. InstrumentTrack( TrackContainer* tc );
  68. virtual ~InstrumentTrack();
  69. // used by instrument
  70. void processAudioBuffer( sampleFrame * _buf, const fpp_t _frames,
  71. NotePlayHandle * _n );
  72. MidiEvent applyMasterKey( const MidiEvent& event );
  73. void processInEvent( const MidiEvent& event, const MidiTime& time = MidiTime(), f_cnt_t offset = 0 ) override;
  74. void processOutEvent( const MidiEvent& event, const MidiTime& time = MidiTime(), f_cnt_t offset = 0 ) override;
  75. // silence all running notes played by this track
  76. void silenceAllNotes( bool removeIPH = false );
  77. bool isSustainPedalPressed() const
  78. {
  79. return m_sustainPedalPressed;
  80. }
  81. f_cnt_t beatLen( NotePlayHandle * _n ) const;
  82. // for capturing note-play-events -> need that for arpeggio,
  83. // filter and so on
  84. void playNote( NotePlayHandle * _n, sampleFrame * _working_buffer );
  85. QString instrumentName() const;
  86. const Instrument *instrument() const
  87. {
  88. return m_instrument;
  89. }
  90. Instrument *instrument()
  91. {
  92. return m_instrument;
  93. }
  94. void deleteNotePluginData( NotePlayHandle * _n );
  95. // name-stuff
  96. void setName( const QString & _new_name ) override;
  97. // translate given key of a note-event to absolute key (i.e.
  98. // add global master-pitch and base-note of this instrument track)
  99. int masterKey( int _midi_key ) const;
  100. // translate pitch to midi-pitch [0,16383]
  101. int midiPitch() const
  102. {
  103. return static_cast<int>( ( ( m_pitchModel.value() + m_pitchModel.range()/2 ) * MidiMaxPitchBend ) / m_pitchModel.range() );
  104. }
  105. /*! \brief Returns current range for pitch bend in semitones */
  106. int midiPitchRange() const
  107. {
  108. return m_pitchRangeModel.value();
  109. }
  110. // play everything in given frame-range - creates note-play-handles
  111. virtual bool play( const MidiTime & _start, const fpp_t _frames,
  112. const f_cnt_t _frame_base, int _tco_num = -1 ) override;
  113. // create new view for me
  114. TrackView * createView( TrackContainerView* tcv ) override;
  115. // create new track-content-object = pattern
  116. TrackContentObject * createTCO( const MidiTime & _pos ) override;
  117. // called by track
  118. virtual void saveTrackSpecificSettings( QDomDocument & _doc,
  119. QDomElement & _parent ) override;
  120. void loadTrackSpecificSettings( const QDomElement & _this ) override;
  121. using Track::setJournalling;
  122. // load instrument whose name matches given one
  123. Instrument * loadInstrument(const QString & _instrument_name,
  124. const Plugin::Descriptor::SubPluginFeatures::Key* key = nullptr,
  125. bool keyFromDnd = false);
  126. AudioPort * audioPort()
  127. {
  128. return &m_audioPort;
  129. }
  130. MidiPort * midiPort()
  131. {
  132. return &m_midiPort;
  133. }
  134. const IntModel *baseNoteModel() const
  135. {
  136. return &m_baseNoteModel;
  137. }
  138. IntModel *baseNoteModel()
  139. {
  140. return &m_baseNoteModel;
  141. }
  142. int baseNote() const;
  143. Piano *pianoModel()
  144. {
  145. return &m_piano;
  146. }
  147. bool isArpeggioEnabled() const
  148. {
  149. return m_arpeggio.m_arpEnabledModel.value();
  150. }
  151. // simple helper for removing midiport-XML-node when loading presets
  152. static void removeMidiPortNode( DataFile& dataFile );
  153. FloatModel * pitchModel()
  154. {
  155. return &m_pitchModel;
  156. }
  157. FloatModel * volumeModel()
  158. {
  159. return &m_volumeModel;
  160. }
  161. FloatModel * panningModel()
  162. {
  163. return &m_panningModel;
  164. }
  165. IntModel* pitchRangeModel()
  166. {
  167. return &m_pitchRangeModel;
  168. }
  169. IntModel * effectChannelModel()
  170. {
  171. return &m_effectChannelModel;
  172. }
  173. void setPreviewMode( const bool );
  174. signals:
  175. void instrumentChanged();
  176. void midiNoteOn( const Note& );
  177. void midiNoteOff( const Note& );
  178. void nameChanged();
  179. void newNote();
  180. void endNote();
  181. protected:
  182. QString nodeName() const override
  183. {
  184. return "instrumenttrack";
  185. }
  186. protected slots:
  187. void updateBaseNote();
  188. void updatePitch();
  189. void updatePitchRange();
  190. void updateEffectChannel();
  191. private:
  192. MidiPort m_midiPort;
  193. NotePlayHandle* m_notes[NumKeys];
  194. NotePlayHandleList m_sustainedNotes;
  195. int m_runningMidiNotes[NumKeys];
  196. QMutex m_midiNotesMutex;
  197. bool m_sustainPedalPressed;
  198. bool m_silentBuffersProcessed;
  199. bool m_previewMode;
  200. IntModel m_baseNoteModel;
  201. NotePlayHandleList m_processHandles;
  202. FloatModel m_volumeModel;
  203. FloatModel m_panningModel;
  204. AudioPort m_audioPort;
  205. FloatModel m_pitchModel;
  206. IntModel m_pitchRangeModel;
  207. IntModel m_effectChannelModel;
  208. BoolModel m_useMasterPitchModel;
  209. Instrument * m_instrument;
  210. InstrumentSoundShaping m_soundShaping;
  211. InstrumentFunctionArpeggio m_arpeggio;
  212. InstrumentFunctionNoteStacking m_noteStacking;
  213. Piano m_piano;
  214. friend class InstrumentTrackView;
  215. friend class InstrumentTrackWindow;
  216. friend class NotePlayHandle;
  217. friend class InstrumentMiscView;
  218. } ;
  219. class InstrumentTrackView : public TrackView
  220. {
  221. Q_OBJECT
  222. public:
  223. InstrumentTrackView( InstrumentTrack * _it, TrackContainerView* tc );
  224. virtual ~InstrumentTrackView();
  225. InstrumentTrackWindow * getInstrumentTrackWindow();
  226. InstrumentTrack * model()
  227. {
  228. return castModel<InstrumentTrack>();
  229. }
  230. const InstrumentTrack * model() const
  231. {
  232. return castModel<InstrumentTrack>();
  233. }
  234. static InstrumentTrackWindow * topLevelInstrumentTrackWindow();
  235. QMenu * midiMenu()
  236. {
  237. return m_midiMenu;
  238. }
  239. void freeInstrumentTrackWindow();
  240. static void cleanupWindowCache();
  241. // Create a menu for assigning/creating channels for this track
  242. QMenu * createFxMenu( QString title, QString newFxLabel ) override;
  243. protected:
  244. void dragEnterEvent( QDragEnterEvent * _dee ) override;
  245. void dropEvent( QDropEvent * _de ) override;
  246. private slots:
  247. void toggleInstrumentWindow( bool _on );
  248. void activityIndicatorPressed();
  249. void activityIndicatorReleased();
  250. void midiInSelected();
  251. void midiOutSelected();
  252. void midiConfigChanged();
  253. void muteChanged();
  254. void assignFxLine( int channelIndex );
  255. void createFxLine();
  256. private:
  257. InstrumentTrackWindow * m_window;
  258. static QQueue<InstrumentTrackWindow *> s_windowCache;
  259. // widgets in track-settings-widget
  260. TrackLabelButton * m_tlb;
  261. Knob * m_volumeKnob;
  262. Knob * m_panningKnob;
  263. FadeButton * m_activityIndicator;
  264. QMenu * m_midiMenu;
  265. QAction * m_midiInputAction;
  266. QAction * m_midiOutputAction;
  267. QPoint m_lastPos;
  268. friend class InstrumentTrackWindow;
  269. } ;
  270. class InstrumentTrackWindow : public QWidget, public ModelView,
  271. public SerializingObjectHook
  272. {
  273. Q_OBJECT
  274. public:
  275. InstrumentTrackWindow( InstrumentTrackView * _tv );
  276. virtual ~InstrumentTrackWindow();
  277. // parent for all internal tab-widgets
  278. TabWidget * tabWidgetParent()
  279. {
  280. return m_tabWidget;
  281. }
  282. InstrumentTrack * model()
  283. {
  284. return castModel<InstrumentTrack>();
  285. }
  286. const InstrumentTrack * model() const
  287. {
  288. return castModel<InstrumentTrack>();
  289. }
  290. void setInstrumentTrackView( InstrumentTrackView * _tv );
  291. InstrumentTrackView *instrumentTrackView()
  292. {
  293. return m_itv;
  294. }
  295. PianoView * pianoView()
  296. {
  297. return m_pianoView;
  298. }
  299. static void dragEnterEventGeneric( QDragEnterEvent * _dee );
  300. void dragEnterEvent( QDragEnterEvent * _dee ) override;
  301. void dropEvent( QDropEvent * _de ) override;
  302. public slots:
  303. void textChanged( const QString & _new_name );
  304. void toggleVisibility( bool _on );
  305. void updateName();
  306. void updateInstrumentView();
  307. protected:
  308. // capture close-events for toggling instrument-track-button
  309. void closeEvent( QCloseEvent * _ce ) override;
  310. void focusInEvent( QFocusEvent * _fe ) override;
  311. void saveSettings( QDomDocument & _doc, QDomElement & _this ) override;
  312. void loadSettings( const QDomElement & _this ) override;
  313. protected slots:
  314. void saveSettingsBtnClicked();
  315. void viewNextInstrument();
  316. void viewPrevInstrument();
  317. private:
  318. void modelChanged() override;
  319. void viewInstrumentInDirection(int d);
  320. //! adjust size of any child widget of the main tab
  321. //! required to keep the old look when using a variable sized tab widget
  322. void adjustTabSize(QWidget *w);
  323. InstrumentTrack * m_track;
  324. InstrumentTrackView * m_itv;
  325. // widgets on the top of an instrument-track-window
  326. QLineEdit * m_nameLineEdit;
  327. LeftRightNav * m_leftRightNav;
  328. Knob * m_volumeKnob;
  329. Knob * m_panningKnob;
  330. Knob * m_pitchKnob;
  331. QLabel * m_pitchLabel;
  332. LcdSpinBox* m_pitchRangeSpinBox;
  333. QLabel * m_pitchRangeLabel;
  334. FxLineLcdSpinBox * m_effectChannelNumber;
  335. // tab-widget with all children
  336. TabWidget * m_tabWidget;
  337. PluginView * m_instrumentView;
  338. InstrumentSoundShapingView * m_ssView;
  339. InstrumentFunctionNoteStackingView* m_noteStackingView;
  340. InstrumentFunctionArpeggioView* m_arpeggioView;
  341. InstrumentMidiIOView * m_midiView;
  342. EffectRackView * m_effectView;
  343. InstrumentMiscView *m_miscView;
  344. // test-piano at the bottom of every instrument-settings-window
  345. PianoView * m_pianoView;
  346. friend class InstrumentView;
  347. } ;
  348. #endif