root/branches/new_fx_rack_and_sample_fun/gui/src/SampleEditor/SampleEditor.cpp @ 625

Revision 625, 15.4 KB (checked in by wolke, 5 years ago)

samples play reverse and pingpong

Line 
1/*
2 * Hydrogen
3 * Copyright(c) 2002-2008 by Alex >Comix< Cominu [comix@users.sourceforge.net]
4 *
5 * http://www.hydrogen-music.org
6 *
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation; either version 2 of the License, or
10 * (at your option) any later version.
11 *
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY, without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
20 *
21 */
22
23#include "SampleEditor.h"
24#include "../HydrogenApp.h"
25#include "InstrumentEditor/InstrumentEditor.h"
26#include "InstrumentEditor/InstrumentEditorPanel.h"
27#include "../widgets/Button.h"
28
29#include "MainSampleWaveDisplay.h"
30#include "DetailWaveDisplay.h"
31#include "TargetWaveDisplay.h"
32
33#include <hydrogen/data_path.h>
34#include <hydrogen/h2_exception.h>
35#include <hydrogen/Preferences.h>
36#include <hydrogen/sample.h>
37#include <hydrogen/audio_engine.h>
38#include <hydrogen/hydrogen.h>
39
40#include <QModelIndex>
41#include <QTreeWidget>
42#include <QMessageBox>
43
44using namespace H2Core;
45using namespace std;
46
47SampleEditor::SampleEditor ( QWidget* pParent, int nSelectedLayer, QString mSamplefilename )
48                : QDialog ( pParent )
49                , Object ( "SampleEditor" )
50                , m_pSampleEditorStatus( true )
51                , m_pSamplefromFile ( NULL )
52                , m_pSelectedLayer ( nSelectedLayer )
53                , m_samplename ( mSamplefilename )
54                , m_pzoomfactor ( 1 )
55                , m_pdetailframe ( 0 )
56                , m_plineColor ( "default" )
57                , m_ponewayStart ( false )
58                , m_ponewayLoop ( false )
59                , m_ponewayEnd ( false )
60                , m_pslframes ( 0 )
61{
62        setupUi ( this );
63        INFOLOG ( "INIT" );
64
65        QString newfilename = mSamplefilename.section( '/', -1 );
66
67        setWindowTitle ( QString( "SampleEditor" + newfilename) );
68        setFixedSize ( width(), height() );
69        installEventFilter( this );
70
71//this new sample give us the not changed real samplelength
72        m_pSamplefromFile = Sample::load( mSamplefilename );
73
74//this
75        unsigned slframes = m_pSamplefromFile->get_n_frames();
76
77        LoopCountSpinBox->setRange(0, 20000 );
78        StartFrameSpinBox->setRange(0, slframes );
79        LoopFrameSpinBox->setRange(0, slframes );
80        EndFrameSpinBox->setRange(0, slframes );
81        EndFrameSpinBox->setValue( slframes );
82
83        getAllFrameInfos();
84        intDisplays();
85       
86
87
88//      m_pSample->set_end_frame( m_end_frame );
89
90// mainSampleview = 624(575) x 265 :-)
91// mainSampleAdjustView = 180 x 265 :-(
92// targetSampleView = 451 x 91 :-( will removed
93// StartFrameSpinBox :-)
94// LoopFrameSpinBox :-)
95// ProcessingTypeComboBox :forward, reverse, pingpong :-)
96// LoopCountSpinBox :-(
97// EndFrameSpinBox :-)
98// FadeOutFrameSpinBox :-(
99// FadeOutTypeComboBox: lin, log :-(
100// ApplyChangesPushButton :-()
101// PlayPushButton :-)
102// RestoreSamplePushButton :-(
103// ClosePushButton :-()
104// verticalzoomSlider
105
106        connect( StartFrameSpinBox, SIGNAL( valueChanged( int ) ), this, SLOT( valueChangedStartFrameSpinBox(int) ) );
107        connect( LoopFrameSpinBox, SIGNAL( valueChanged( int ) ), this, SLOT( valueChangedLoopFrameSpinBox(int) ) );
108        connect( EndFrameSpinBox, SIGNAL( valueChanged( int ) ), this, SLOT( valueChangedEndFrameSpinBox(int) ) );
109
110        m_pTimer = new QTimer(this);
111        connect(m_pTimer, SIGNAL(timeout()), this, SLOT(updateMainsamplePostionRuler()));
112}
113
114
115
116
117
118SampleEditor::~SampleEditor()
119{
120        delete m_pMainSampleWaveDisplay;
121        delete m_pSampleAdjustView;
122        delete m_pTargetSampleView;
123        delete m_pSamplefromFile;
124        INFOLOG ( "DESTROY" );
125}
126
127
128//this
129void SampleEditor::getAllFrameInfos()
130{
131        H2Core::Instrument *m_pInstrument = NULL;
132        Sample* pSample = NULL;
133        Song *pSong = Hydrogen::get_instance()->getSong();
134        if (pSong != NULL) {
135                InstrumentList *pInstrList = pSong->get_instrument_list();
136                int nInstr = Hydrogen::get_instance()->getSelectedInstrumentNumber();
137                if ( nInstr >= (int)pInstrList->get_size() ) {
138                        nInstr = -1;
139                }
140
141                if (nInstr == -1) {
142                        m_pInstrument = NULL;
143                }
144                else {
145                        m_pInstrument = pInstrList->get( nInstr );
146                        //INFOLOG( "new instr: " + m_pInstrument->m_sName );
147                }
148        }
149        H2Core::InstrumentLayer *pLayer = m_pInstrument->get_layer( m_pSelectedLayer );
150        if ( pLayer ) {
151                pSample = pLayer->get_sample();
152        }
153
154//this values are needed if we restore a sample from from disk if a new song with sample changes will load
155        m_sample_is_modified = pSample->get_sample_is_modified();
156        m_sample_mode = pSample->get_sample_mode();
157        m_start_frame = pSample->get_start_frame();
158        m_loop_frame = pSample->get_loop_frame();
159        m_repeats = pSample->get_repeats();
160        m_end_frame = m_pSamplefromFile->get_end_frame();
161
162        m_fade_out_startframe = pSample->get_fade_out_startframe();
163        m_fade_out_type = pSample->get_fade_out_type();
164       
165}
166
167
168void SampleEditor::getAllLocalFrameInfos()
169{
170        m_start_frame = StartFrameSpinBox->value();
171        m_loop_frame = LoopFrameSpinBox->value();
172        m_repeats = LoopCountSpinBox->value();
173        m_end_frame = EndFrameSpinBox->value();
174
175}
176
177void SampleEditor::intDisplays()
178{
179        H2Core::Instrument *m_pInstrument = NULL;
180        Song *pSong = Hydrogen::get_instance()->getSong();
181        if (pSong != NULL) {
182                InstrumentList *pInstrList = pSong->get_instrument_list();
183                int nInstr = Hydrogen::get_instance()->getSelectedInstrumentNumber();
184                if ( nInstr >= (int)pInstrList->get_size() ) {
185                        nInstr = -1;
186                }
187
188                if (nInstr == -1) {
189                        m_pInstrument = NULL;
190                }
191                else {
192                        m_pInstrument = pInstrList->get( nInstr );
193                        //INFOLOG( "new instr: " + m_pInstrument->m_sName );
194                }
195        }
196
197        H2Core::InstrumentLayer *pLayer = m_pInstrument->get_layer( m_pSelectedLayer );
198
199        QApplication::setOverrideCursor(Qt::WaitCursor);
200
201// wavedisplays
202        m_divider = m_pSamplefromFile->get_n_frames() / 574.0F;
203        m_pMainSampleWaveDisplay = new MainSampleWaveDisplay( mainSampleview );
204        m_pMainSampleWaveDisplay->updateDisplay( m_pSamplefromFile->get_filename() );
205        m_pMainSampleWaveDisplay->move( 1, 1 );
206
207        m_pSampleAdjustView = new DetailWaveDisplay( mainSampleAdjustView );
208        m_pSampleAdjustView->updateDisplay( m_pSamplefromFile->get_filename() );
209        m_pSampleAdjustView->move( 1, 1 );
210
211        m_pTargetSampleView = new TargetWaveDisplay( targetSampleView );
212        m_pTargetSampleView->updateDisplay( pLayer );
213        m_pTargetSampleView->move( 1, 1 );
214
215
216        QApplication::restoreOverrideCursor();
217
218}
219
220
221
222
223void SampleEditor::on_ClosePushButton_clicked()
224{
225        if ( !m_pSampleEditorStatus ){
226                int err = QMessageBox::information( this, "Hydrogen", tr( "Unsaved changes left. This changes will be lost. \nAre you sure?"), tr("&Ok"), tr("&Cancel"), 0, 1 );
227                if ( err == 0 ){
228                        m_pSampleEditorStatus = true;
229                        accept();       
230                }else
231                {
232                        return;
233                }
234        }
235        accept();
236}
237
238
239
240void SampleEditor::on_PrevChangesPushButton_clicked()
241{
242        getAllLocalFrameInfos();       
243        createNewLayer();
244        m_pSampleEditorStatus = true;
245       
246}
247
248
249
250bool SampleEditor::getCloseQuestion()
251{
252        bool close = false;
253        int err = QMessageBox::information( this, "Hydrogen", tr( "Close dialog! maybe there is some unsaved work on sample.\nAre you sure?"), tr("&Ok"), tr("&Cancel"), 0, 1 );
254        if ( err == 0 ) close = true;
255        return close;
256}
257
258
259
260/*
261void SampleEditor::getAllSampleProps()
262{
263
264        m_pSample->set_sample_is_modified( m_sample_is_modified );
265        m_pSample->set_sample_mode( m_sample_mode );
266        m_pSample->set_start_frame( m_start_frame );
267        m_pSample->set_loop_frame( m_loop_frame );
268        m_pSample->set_repeats( m_repeats );
269        m_pSample->set_end_frame( m_end_frame );
270        ERRORLOG( QString("setAllSampleProps: %1").arg(m_end_frame) );
271        m_pSample->set_fade_out_startframe( m_fade_out_startframe );
272        m_pSample->set_fade_out_type( m_fade_out_type );
273
274}
275*/
276
277
278void SampleEditor::createNewLayer()
279{
280        if ( !m_pSampleEditorStatus ){
281//              getAllFrameInfos();
282               
283                Sample *editSample = Sample::load_edit_wave( m_samplename,
284                                                            m_start_frame,
285                                                            m_loop_frame,
286                                                            m_end_frame,
287                                                            m_repeats,
288                                                            m_sample_mode);
289
290                AudioEngine::get_instance()->lock( "SampeEditor::insert new sample" );
291
292                H2Core::Instrument *m_pInstrument = NULL;
293                Song *pSong = Hydrogen::get_instance()->getSong();
294                if (pSong != NULL) {
295                        InstrumentList *pInstrList = pSong->get_instrument_list();
296                        int nInstr = Hydrogen::get_instance()->getSelectedInstrumentNumber();
297                        if ( nInstr >= (int)pInstrList->get_size() ) {
298                                nInstr = -1;
299                        }
300       
301                        if (nInstr == -1) {
302                                m_pInstrument = NULL;
303                        }
304                        else {
305                                m_pInstrument = pInstrList->get( nInstr );
306                                //INFOLOG( "new instr: " + m_pInstrument->m_sName );
307                        }
308                }
309       
310                H2Core::InstrumentLayer *pLayer = m_pInstrument->get_layer( m_pSelectedLayer );
311
312                Sample *oldSample = pLayer->get_sample();
313                delete oldSample;
314       
315                // insert new sample from newInstrument
316                pLayer->set_sample( editSample );
317
318                AudioEngine::get_instance()->unlock();
319                m_pTargetSampleView->updateDisplay( pLayer );
320                }
321               
322}
323
324void SampleEditor::mouseReleaseEvent(QMouseEvent *ev)
325{
326
327}
328
329
330
331void SampleEditor::returnAllMainWaveDisplayValues()
332{
333//      QMessageBox::information ( this, "Hydrogen", trUtf8 ( "jep %1" ).arg(m_pSample->get_n_frames()));
334        m_sample_is_modified = true;
335        m_start_frame = m_pMainSampleWaveDisplay->m_pStartFramePosition * m_divider - 25 * m_divider;
336        m_loop_frame = m_pMainSampleWaveDisplay->m_pLoopFramePosition  * m_divider - 25 * m_divider;
337        m_end_frame = m_pMainSampleWaveDisplay->m_pEndFramePosition  * m_divider - 25 * m_divider ;
338
339        StartFrameSpinBox->setValue( m_start_frame );
340        LoopFrameSpinBox->setValue( m_loop_frame );
341        EndFrameSpinBox->setValue( m_end_frame );
342        m_ponewayStart = true; 
343        m_ponewayLoop = true;
344        m_ponewayEnd = true;
345}
346
347
348
349void SampleEditor::valueChangedStartFrameSpinBox( int )
350{
351        m_pdetailframe = StartFrameSpinBox->value();
352        m_plineColor = "Start";
353        if ( !m_ponewayStart ){
354                m_pMainSampleWaveDisplay->m_pStartFramePosition = StartFrameSpinBox->value() / m_divider + 25 ;
355                m_pMainSampleWaveDisplay->updateDisplayPointer();
356                m_pSampleAdjustView->setDetailSamplePosition( m_pdetailframe, m_pzoomfactor , m_plineColor);
357                m_start_frame = StartFrameSpinBox->value();
358//              m_pMainSampleWaveDisplay->testPositionFromSampleeditor();
359                               
360        }else
361        {
362                m_pSampleAdjustView->setDetailSamplePosition( m_pdetailframe, m_pzoomfactor , m_plineColor);
363                m_ponewayStart = false;
364        }
365        testPositionsSpinBoxes();
366        m_pSampleEditorStatus = false;
367        //QMessageBox::information ( this, "Hydrogen", trUtf8 ( "jep %1" ).arg(StartFrameSpinBox->value() / m_divider + 25 ));
368}
369
370
371
372void SampleEditor::valueChangedLoopFrameSpinBox( int )
373{       
374        m_pdetailframe = LoopFrameSpinBox->value();
375        m_plineColor = "Loop";
376        if ( !m_ponewayLoop ){
377                m_pMainSampleWaveDisplay->m_pLoopFramePosition = LoopFrameSpinBox->value() / m_divider + 25 ;
378                m_pMainSampleWaveDisplay->updateDisplayPointer();
379                m_pSampleAdjustView->setDetailSamplePosition( m_pdetailframe, m_pzoomfactor , m_plineColor);
380                m_loop_frame = LoopFrameSpinBox->value();
381        }else
382        {
383                m_pSampleAdjustView->setDetailSamplePosition( m_pdetailframe, m_pzoomfactor , m_plineColor);
384                m_ponewayLoop = false;
385        }
386        testPositionsSpinBoxes();
387        m_pSampleEditorStatus = false;
388}
389
390
391
392void SampleEditor::valueChangedEndFrameSpinBox( int )
393{
394        m_pdetailframe = EndFrameSpinBox->value();
395        m_plineColor = "End";
396        if ( !m_ponewayEnd ){
397                m_pMainSampleWaveDisplay->m_pEndFramePosition = EndFrameSpinBox->value() / m_divider + 25 ;
398                m_pMainSampleWaveDisplay->updateDisplayPointer();
399                m_pSampleAdjustView->setDetailSamplePosition( m_pdetailframe, m_pzoomfactor , m_plineColor);
400                m_end_frame = EndFrameSpinBox->value();
401        }else
402        {
403                m_ponewayEnd = false;
404                m_pSampleAdjustView->setDetailSamplePosition( m_pdetailframe, m_pzoomfactor , m_plineColor);
405        }
406        testPositionsSpinBoxes();
407        m_pSampleEditorStatus = false;
408}
409
410
411void SampleEditor::on_PlayPushButton_clicked()
412{
413
414        const int selectedlayer = InstrumentEditorPanel::getInstance()->getselectedLayer();
415        const float pan_L = 0.5f;
416        const float pan_R = 0.5f;
417        const int nLength = -1;
418        const float fPitch = 0.0f;
419        Song *pSong = Hydrogen::get_instance()->getSong();
420       
421        Instrument *pInstr = pSong->get_instrument_list()->get( Hydrogen::get_instance()->getSelectedInstrumentNumber() );
422       
423        Note *pNote = new Note( pInstr, 0, pInstr->get_layer( selectedlayer )->get_end_velocity() - 0.01, pan_L, pan_R, nLength, fPitch);
424        AudioEngine::get_instance()->get_sampler()->note_on(pNote);
425
426
427        setSamplelengthFrames();
428        m_pMainSampleWaveDisplay->paintLocatorEvent( StartFrameSpinBox->value() / m_divider + 24 , true);
429        m_pSampleAdjustView->setDetailSamplePosition( m_start_frame, m_pzoomfactor , 0);
430        m_pTimer->start(40);    // update ruler at 25 fps       
431        m_prealtimeframeend = Hydrogen::get_instance()->getRealtimeFrames() + m_end_frame - m_start_frame;
432       
433}
434
435void SampleEditor::on_PlayOrigPushButton_clicked()
436{
437        Sample *pNewSample = Sample::load( m_samplename );
438        if ( pNewSample ){
439                int length = ( ( pNewSample->get_n_frames() / pNewSample->get_sample_rate() + 1) * 100 );
440                AudioEngine::get_instance()->get_sampler()->preview_sample( pNewSample, length );
441        }
442
443        m_pslframes = pNewSample->get_n_frames();
444        m_pMainSampleWaveDisplay->paintLocatorEvent( StartFrameSpinBox->value() / m_divider + 24 , true);
445        m_pSampleAdjustView->setDetailSamplePosition( m_start_frame, m_pzoomfactor , 0);
446        m_pTimer->start(40);    // update ruler at 25 fps       
447        m_prealtimeframeend = Hydrogen::get_instance()->getRealtimeFrames() + m_end_frame - m_start_frame;
448}
449
450
451void SampleEditor::updateMainsamplePostionRuler()
452{
453        unsigned long realpos = Hydrogen::get_instance()->getRealtimeFrames();
454        if ( realpos < m_prealtimeframeend ){
455                unsigned frame = m_pslframes - ( m_prealtimeframeend  - realpos );
456                m_pMainSampleWaveDisplay->paintLocatorEvent( frame / m_divider + 25 , true);
457                m_pSampleAdjustView->setDetailSamplePosition( frame, m_pzoomfactor , 0);
458//              ERRORLOG( QString("sampleval: %1").arg(frame) );
459        }else
460        {
461                m_pMainSampleWaveDisplay->paintLocatorEvent( -1 , false);
462//              m_pSampleAdjustView->setDetailSamplePosition( 0, m_pzoomfactor , 0);
463                m_pTimer->stop();
464        }
465}
466
467
468
469void SampleEditor::setSamplelengthFrames()
470{
471getAllLocalFrameInfos();
472//      getAllFrameInfos();
473
474        //create new  sample length
475        unsigned onesamplelength =  m_end_frame - m_start_frame;
476        unsigned looplength =  m_end_frame - m_loop_frame ;
477        unsigned repeatslength = looplength * m_repeats;
478        unsigned newlength = 0;
479        if (onesamplelength == looplength){     
480                newlength = onesamplelength + onesamplelength * m_repeats ;
481        }else
482        {
483                newlength =onesamplelength + repeatslength;
484        }
485        m_pslframes = newlength;
486}
487
488
489
490void SampleEditor::on_LoopCountSpinBox_valueChanged( int )
491{
492        m_repeats = LoopCountSpinBox->value() ;
493        m_pSampleEditorStatus = false;
494}
495
496
497void SampleEditor::on_ProcessingTypeComboBox_currentIndexChanged( int )
498{
499        switch ( ProcessingTypeComboBox->currentIndex() ){
500                case 0 ://
501                        m_sample_mode = "forward";
502                        break;
503                case 1 ://
504                        m_sample_mode = "reverse";
505                        break;
506                case 2 ://
507                        m_sample_mode = "pingpong";
508                        break;
509                default:
510                        m_sample_mode = "forward";
511        }
512        m_pSampleEditorStatus = false;
513}
514
515
516
517
518void SampleEditor::on_verticalzoomSlider_valueChanged( int value )
519{
520        m_pzoomfactor = value / 10 +1;
521        m_pSampleAdjustView->setDetailSamplePosition( m_pdetailframe, m_pzoomfactor, m_plineColor );
522}
523
524
525void SampleEditor::testPositionsSpinBoxes()
526{
527//m_start_frame;
528//m_loop_frame;
529//m_end_frame;
530        if (  m_start_frame > m_loop_frame ) m_loop_frame = m_start_frame;
531        if (  m_start_frame > m_end_frame ) m_end_frame = m_start_frame;
532        if (  m_loop_frame > m_end_frame ) m_end_frame = m_loop_frame;
533        if (  m_end_frame < m_loop_frame ) m_loop_frame = m_end_frame;
534        if (  m_end_frame < m_start_frame ) m_start_frame = m_end_frame;
535        StartFrameSpinBox->setValue( m_start_frame );
536        LoopFrameSpinBox->setValue( m_loop_frame );
537        EndFrameSpinBox->setValue( m_end_frame );
538}
Note: See TracBrowser for help on using the browser.