mutex, detuning helpers, GUI updates, play handles, many many changes... (6)
git-svn-id: https://lmms.svn.sf.net/svnroot/lmms/trunk/lmms@484 0778d3d1-df1d-0410-868b-ea421aaaa00d
This commit is contained in:
@@ -6,6 +6,7 @@
|
||||
#include "src/lib/string_pair_drag.cpp"
|
||||
#include "src/lib/journalling_object.cpp"
|
||||
#include "src/lib/project_journal.cpp"
|
||||
#include "src/lib/project_version.cpp"
|
||||
#include "src/lib/embed.cpp"
|
||||
#include "src/lib/base64.cpp"
|
||||
#include "src/lib/mmp.cpp"
|
||||
@@ -27,6 +28,7 @@
|
||||
#include "src/core/piano_roll.cpp"
|
||||
#include "src/core/arp_and_chords_tab_widget.cpp"
|
||||
#include "src/core/automation_editor.cpp"
|
||||
#include "src/core/automation_pattern.cpp"
|
||||
#include "src/core/about_dialog.cpp"
|
||||
#include "src/core/instrument.cpp"
|
||||
#include "src/core/main.cpp"
|
||||
@@ -65,7 +67,6 @@
|
||||
#include "src/audio/audio_sample_recorder.cpp"
|
||||
#include "src/audio/audio_file_wave.cpp"
|
||||
#include "src/lmms_single_source.cpp"
|
||||
#include "src/tracks/automation_pattern.cpp"
|
||||
#include "src/tracks/automation_track.cpp"
|
||||
#include "src/tracks/pattern.cpp"
|
||||
#include "src/tracks/bb_track.cpp"
|
||||
|
||||
@@ -1,272 +0,0 @@
|
||||
#ifndef SINGLE_SOURCE_COMPILE
|
||||
|
||||
/*
|
||||
* automation_pattern.cpp - implementation of class automationPattern which
|
||||
* holds dynamic values
|
||||
*
|
||||
* Copyright (c) 2006-2007 Javier Serrano Polo <jasp00/at/users.sourceforge.net>
|
||||
*
|
||||
* This file is part of Linux MultiMedia Studio - http://lmms.sourceforge.net
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public
|
||||
* License along with this program (see COPYING); if not, write to the
|
||||
* Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
|
||||
* Boston, MA 02110-1301 USA.
|
||||
*
|
||||
*/
|
||||
|
||||
|
||||
#include "qt3support.h"
|
||||
|
||||
#ifdef QT4
|
||||
|
||||
#include <Qt/QtXml>
|
||||
|
||||
#else
|
||||
|
||||
#include <qdom.h>
|
||||
#define value data
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
#include "automation_pattern.h"
|
||||
#include "templates.h"
|
||||
#include "automation_editor.h"
|
||||
#include "engine.h"
|
||||
|
||||
|
||||
|
||||
|
||||
automationPattern::automationPattern( track * _track, levelObject * _object ) :
|
||||
m_track( _track ),
|
||||
m_object( _object ),
|
||||
m_update_first( TRUE )
|
||||
{
|
||||
init();
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
automationPattern::automationPattern( const automationPattern & _pat_to_copy ) :
|
||||
m_track( _pat_to_copy.m_track ),
|
||||
m_object( _pat_to_copy.m_object ),
|
||||
m_update_first( _pat_to_copy.m_update_first )
|
||||
{
|
||||
for( timeMap::const_iterator it = _pat_to_copy.m_time_map.begin();
|
||||
it != _pat_to_copy.m_time_map.end(); ++it )
|
||||
{
|
||||
m_time_map[it.key()] = it.value();
|
||||
}
|
||||
|
||||
init();
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
automationPattern::automationPattern( const automationPattern & _pat_to_copy,
|
||||
levelObject * _object ) :
|
||||
m_track( _pat_to_copy.m_track ),
|
||||
m_object( _object ),
|
||||
m_update_first( _pat_to_copy.m_update_first )
|
||||
{
|
||||
for( timeMap::const_iterator it = _pat_to_copy.m_time_map.begin();
|
||||
it != _pat_to_copy.m_time_map.end(); ++it )
|
||||
{
|
||||
m_time_map[it.key()] = it.value();
|
||||
}
|
||||
|
||||
init();
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
automationPattern::~automationPattern()
|
||||
{
|
||||
if( m_track )
|
||||
{
|
||||
m_track->removeAutomationPattern( this );
|
||||
}
|
||||
|
||||
if( engine::getAutomationEditor()
|
||||
&& engine::getAutomationEditor()->currentPattern() == this )
|
||||
{
|
||||
engine::getAutomationEditor()->setCurrentPattern( NULL );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
void automationPattern::init( void )
|
||||
{
|
||||
if( m_track )
|
||||
{
|
||||
m_track->addAutomationPattern( this );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
midiTime automationPattern::length( void ) const
|
||||
{
|
||||
Sint32 max_length = 0;
|
||||
|
||||
for( timeMap::const_iterator it = m_time_map.begin();
|
||||
it != m_time_map.end();
|
||||
++it )
|
||||
{
|
||||
max_length = tMax<Sint32>( max_length, -it.key() );
|
||||
}
|
||||
if( max_length % 64 == 0 )
|
||||
{
|
||||
return( midiTime( tMax<Sint32>( max_length, 64 ) ) );
|
||||
}
|
||||
return( midiTime( tMax( midiTime( max_length ).getTact() + 1, 1 ),
|
||||
0 ) );
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
midiTime automationPattern::putValue( const midiTime & _time, const int _value,
|
||||
const bool _quant_pos )
|
||||
{
|
||||
midiTime new_time = _quant_pos ?
|
||||
note::quantized( _time,
|
||||
engine::getAutomationEditor()->quantization() ) :
|
||||
_time;
|
||||
|
||||
m_time_map[-new_time] = _value;
|
||||
|
||||
return( new_time );
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
void automationPattern::removeValue( const midiTime & _time )
|
||||
{
|
||||
if( _time != 0 )
|
||||
{
|
||||
m_time_map.remove( -_time );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
void automationPattern::clear( void )
|
||||
{
|
||||
m_time_map.clear();
|
||||
if( engine::getAutomationEditor()->currentPattern() == this )
|
||||
{
|
||||
engine::getAutomationEditor()->update();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
int automationPattern::valueAt( const midiTime & _time )
|
||||
{
|
||||
return( m_time_map.lowerBound( -_time ).value() );
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
void automationPattern::saveSettings( QDomDocument & _doc, QDomElement & _this )
|
||||
{
|
||||
for( timeMap::iterator it = m_time_map.begin(); it != m_time_map.end();
|
||||
++it )
|
||||
{
|
||||
QDomElement element = _doc.createElement( "time" );
|
||||
element.setAttribute( "pos", -it.key() );
|
||||
element.setAttribute( "value", m_object->levelToLabel(
|
||||
it.value() ) );
|
||||
_this.appendChild( element );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
void automationPattern::loadSettings( const QDomElement & _this )
|
||||
{
|
||||
clear();
|
||||
|
||||
for( QDomNode node = _this.firstChild(); !node.isNull();
|
||||
node = node.nextSibling() )
|
||||
{
|
||||
QDomElement element = node.toElement();
|
||||
if( element.isNull() || element.tagName() != "time" )
|
||||
{
|
||||
continue;
|
||||
}
|
||||
m_time_map[-element.attribute( "pos" ).toInt()]
|
||||
= m_object->labelToLevel(
|
||||
element.attribute( "value" ) );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
void automationPattern::openInAutomationEditor( void )
|
||||
{
|
||||
engine::getAutomationEditor()->setCurrentPattern( this );
|
||||
engine::getAutomationEditor()->show();
|
||||
engine::getAutomationEditor()->setFocus();
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
const QString automationPattern::name( void )
|
||||
{
|
||||
QString widget_name = dynamic_cast<QWidget *>( m_object )
|
||||
->accessibleName();
|
||||
if( m_track )
|
||||
{
|
||||
return( m_track->name() + " - " + widget_name );
|
||||
}
|
||||
else
|
||||
{
|
||||
return( widget_name );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
void automationPattern::processMidiTime( const midiTime & _time )
|
||||
{
|
||||
if( _time >= 0 )
|
||||
{
|
||||
timeMap::iterator it = m_time_map.lowerBound( -_time );
|
||||
m_object->setLevel( it.value() );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
#undef value
|
||||
|
||||
#include "automation_pattern.moc"
|
||||
|
||||
|
||||
#endif
|
||||
@@ -45,13 +45,14 @@
|
||||
|
||||
|
||||
#include "bb_track.h"
|
||||
#include "song_editor.h"
|
||||
#include "bb_editor.h"
|
||||
#include "gui_templates.h"
|
||||
#include "name_label.h"
|
||||
#include "embed.h"
|
||||
#include "engine.h"
|
||||
#include "gui_templates.h"
|
||||
#include "mixer.h"
|
||||
#include "name_label.h"
|
||||
#include "rename_dialog.h"
|
||||
#include "song_editor.h"
|
||||
#include "templates.h"
|
||||
|
||||
|
||||
@@ -368,6 +369,8 @@ bbTrack::bbTrack( trackContainer * _tc ) :
|
||||
|
||||
bbTrack::~bbTrack()
|
||||
{
|
||||
engine::getMixer()->removePlayHandles( this );
|
||||
|
||||
csize bb = s_infoMap[this];
|
||||
engine::getBBEditor()->removeBB( bb );
|
||||
for( infoMap::iterator it = s_infoMap.begin(); it != s_infoMap.end();
|
||||
|
||||
@@ -61,35 +61,37 @@
|
||||
|
||||
|
||||
#include "instrument_track.h"
|
||||
#include "pattern.h"
|
||||
#include "main_window.h"
|
||||
#include "song_editor.h"
|
||||
#include "effect_board.h"
|
||||
#include "envelope_tab_widget.h"
|
||||
#include "arp_and_chords_tab_widget.h"
|
||||
#include "instrument.h"
|
||||
#include "audio_port.h"
|
||||
#include "automation_pattern.h"
|
||||
#include "config_mgr.h"
|
||||
#include "debug.h"
|
||||
#include "effect_board.h"
|
||||
#include "effect_chain.h"
|
||||
#include "effect_tab_widget.h"
|
||||
#include "embed.h"
|
||||
#include "engine.h"
|
||||
#include "envelope_tab_widget.h"
|
||||
#include "fade_button.h"
|
||||
#include "gui_templates.h"
|
||||
#include "instrument.h"
|
||||
#include "lcd_spinbox.h"
|
||||
#include "led_checkbox.h"
|
||||
#include "main_window.h"
|
||||
#include "midi_client.h"
|
||||
#include "midi_port.h"
|
||||
#include "midi_tab_widget.h"
|
||||
#include "note_play_handle.h"
|
||||
#include "sample_play_handle.h"
|
||||
#include "embed.h"
|
||||
#include "fade_button.h"
|
||||
#include "lcd_spinbox.h"
|
||||
#include "led_checkbox.h"
|
||||
#include "piano_widget.h"
|
||||
#include "surround_area.h"
|
||||
#include "tooltip.h"
|
||||
#include "tab_widget.h"
|
||||
#include "config_mgr.h"
|
||||
#include "debug.h"
|
||||
#include "mmp.h"
|
||||
#include "note_play_handle.h"
|
||||
#include "pattern.h"
|
||||
#include "piano_widget.h"
|
||||
#include "sample_play_handle.h"
|
||||
#include "song_editor.h"
|
||||
#include "string_pair_drag.h"
|
||||
#include "surround_area.h"
|
||||
#include "tab_widget.h"
|
||||
#include "tooltip.h"
|
||||
#include "volume_knob.h"
|
||||
#include "effect_chain.h"
|
||||
#include "effect_tab_widget.h"
|
||||
|
||||
|
||||
|
||||
@@ -121,7 +123,6 @@ instrumentTrack::instrumentTrack( trackContainer * _tc ) :
|
||||
tr( "unnamed_channel" ) ) ),
|
||||
m_audioPort( new audioPort( tr( "unnamed_channel" ) ) ),
|
||||
m_notes(),
|
||||
m_notesMutex(),
|
||||
m_baseTone( A ),
|
||||
m_baseOctave( OCTAVE_4 ),
|
||||
m_instrument( NULL ),
|
||||
@@ -133,12 +134,10 @@ instrumentTrack::instrumentTrack( trackContainer * _tc ) :
|
||||
m_midiOutputID( -1 )
|
||||
#endif
|
||||
{
|
||||
m_notesMutex.lock();
|
||||
for( int i = 0; i < NOTES; ++i )
|
||||
{
|
||||
m_notes[i] = NULL;
|
||||
}
|
||||
m_notesMutex.unlock();
|
||||
|
||||
|
||||
#ifdef QT4
|
||||
@@ -393,7 +392,8 @@ instrumentTrack::instrumentTrack( trackContainer * _tc ) :
|
||||
|
||||
instrumentTrack::~instrumentTrack()
|
||||
{
|
||||
invalidateAllMyNPH();
|
||||
engine::getMixer()->removePlayHandles( this );
|
||||
delete m_effWidget;
|
||||
delete m_audioPort;
|
||||
engine::getMixer()->getMIDIClient()->removePort( m_midiPort );
|
||||
}
|
||||
@@ -522,21 +522,6 @@ void instrumentTrack::midiConfigChanged( bool )
|
||||
|
||||
|
||||
|
||||
float instrumentTrack::frequency( notePlayHandle * _n ) const
|
||||
{
|
||||
float pitch = (float)( _n->tone() - m_baseTone +
|
||||
engine::getSongEditor()->masterPitch() ) / 12.0f +
|
||||
(float)( _n->octave() - m_baseOctave );
|
||||
if( _n->detuning() )
|
||||
{
|
||||
pitch += _n->detuning()->value() / 12.0f;
|
||||
}
|
||||
return( BASE_FREQ * powf( 2.0f, pitch ) );
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
f_cnt_t instrumentTrack::beatLen( notePlayHandle * _n ) const
|
||||
{
|
||||
if( m_instrument != NULL )
|
||||
@@ -628,7 +613,6 @@ void instrumentTrack::processAudioBuffer( sampleFrame * _buf,
|
||||
void instrumentTrack::processInEvent( const midiEvent & _me,
|
||||
const midiTime & _time )
|
||||
{
|
||||
m_notesMutex.lock();
|
||||
switch( _me.m_type )
|
||||
{
|
||||
case NOTE_ON:
|
||||
@@ -653,19 +637,10 @@ void instrumentTrack::processInEvent( const midiEvent & _me,
|
||||
_time.frames(
|
||||
engine::framesPerTact64th() ),
|
||||
valueRanges<f_cnt_t>::max, n );
|
||||
// as mixer::addPlayHandle() might
|
||||
// delete note (when running into
|
||||
// critical XRuns) which will call
|
||||
// deleteNotePluginData which locks
|
||||
// this mutex, we have to unlock
|
||||
// it here temporarily
|
||||
m_notesMutex.unlock();
|
||||
if( engine::getMixer()->addPlayHandle(
|
||||
nph ) )
|
||||
{
|
||||
m_notesMutex.lock();
|
||||
m_notes[_me.key()] = nph;
|
||||
m_notesMutex.unlock();
|
||||
}
|
||||
return;
|
||||
}
|
||||
@@ -724,7 +699,6 @@ void instrumentTrack::processInEvent( const midiEvent & _me,
|
||||
_me.m_type );
|
||||
break;
|
||||
}
|
||||
m_notesMutex.unlock();
|
||||
}
|
||||
|
||||
|
||||
@@ -733,15 +707,35 @@ void instrumentTrack::processInEvent( const midiEvent & _me,
|
||||
void instrumentTrack::processOutEvent( const midiEvent & _me,
|
||||
const midiTime & _time )
|
||||
{
|
||||
if( _me.m_type == NOTE_ON && !configManager::inst()->value( "ui",
|
||||
"disablechannelactivityindicators" ).toInt() )
|
||||
switch( _me.m_type )
|
||||
{
|
||||
//QMutexLocker ml( &m_notesMutex );
|
||||
if( m_notes[_me.key()] != NULL )
|
||||
{
|
||||
return;
|
||||
}
|
||||
m_tswActivityIndicator->activate();
|
||||
case NOTE_ON:
|
||||
if( !configManager::inst()->value( "ui",
|
||||
"manualchannelpiano" ).toInt() )
|
||||
{
|
||||
m_pianoWidget->setKeyState( _me.key(), TRUE );
|
||||
}
|
||||
if( !configManager::inst()->value( "ui",
|
||||
"disablechannelactivityindicators" ).toInt() )
|
||||
{
|
||||
if( m_notes[_me.key()] != NULL )
|
||||
{
|
||||
return;
|
||||
}
|
||||
m_tswActivityIndicator->activate();
|
||||
}
|
||||
break;
|
||||
|
||||
case NOTE_OFF:
|
||||
if( !configManager::inst()->value( "ui",
|
||||
"manualchannelpiano" ).toInt() )
|
||||
{
|
||||
m_pianoWidget->setKeyState( _me.key(), FALSE );
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
// if appropriate, midi-port does futher routing
|
||||
m_midiPort->processOutEvent( _me, _time );
|
||||
@@ -814,7 +808,6 @@ void instrumentTrack::deleteNotePluginData( notePlayHandle * _n )
|
||||
m_instrument->deleteNotePluginData( _n );
|
||||
}
|
||||
|
||||
m_notesMutex.lock();
|
||||
// Notes deleted when keys still pressed
|
||||
if( m_notes[_n->key()] == _n )
|
||||
{
|
||||
@@ -827,7 +820,6 @@ void instrumentTrack::deleteNotePluginData( notePlayHandle * _n )
|
||||
m_notes[_n->key()] = NULL;
|
||||
emit noteDone( done_note );
|
||||
}
|
||||
m_notesMutex.unlock();
|
||||
}
|
||||
|
||||
|
||||
@@ -901,13 +893,21 @@ void instrumentTrack::setSurroundAreaPos( const QPoint & _p )
|
||||
|
||||
void instrumentTrack::setBaseNote( Uint32 _new_note, bool _modified )
|
||||
{
|
||||
engine::getMixer()->lock();
|
||||
setBaseTone( (tones)( _new_note % NOTES_PER_OCTAVE ) );
|
||||
setBaseOctave( (octaves)( _new_note / NOTES_PER_OCTAVE ) );
|
||||
|
||||
for( vlist<notePlayHandle *>::iterator it = m_processHandles.begin();
|
||||
it != m_processHandles.end(); ++it )
|
||||
{
|
||||
( *it )->updateFrequency();
|
||||
}
|
||||
engine::getMixer()->unlock();
|
||||
|
||||
if( _modified )
|
||||
{
|
||||
engine::getSongEditor()->setModified();
|
||||
}
|
||||
emit baseNoteChanged();
|
||||
}
|
||||
|
||||
|
||||
@@ -1030,9 +1030,9 @@ bool FASTCALL instrumentTrack::play( const midiTime & _start,
|
||||
}
|
||||
|
||||
// get all notes from the given pattern...
|
||||
noteVector & notes = p->notes();
|
||||
const noteVector & notes = p->notes();
|
||||
// ...and set our index to zero
|
||||
noteVector::iterator it = notes.begin();
|
||||
noteVector::const_iterator it = notes.begin();
|
||||
#if SINGERBOT_SUPPORT
|
||||
int note_idx = 0;
|
||||
#endif
|
||||
@@ -1343,23 +1343,14 @@ void instrumentTrack::dropEvent( QDropEvent * _de )
|
||||
|
||||
void instrumentTrack::invalidateAllMyNPH( void )
|
||||
{
|
||||
// note-play-handles check track-type to determine whether their
|
||||
// channel-track is being deleted (if this is the case, they
|
||||
// invalidate themselves)
|
||||
m_trackType = NULL_TRACK;
|
||||
|
||||
m_notesMutex.lock();
|
||||
for( int i = 0; i < NOTES; ++i )
|
||||
{
|
||||
m_notes[i] = NULL;
|
||||
}
|
||||
m_notesMutex.unlock();
|
||||
|
||||
// invalidate all note-play-handles linked to this channel
|
||||
m_processHandles.clear();
|
||||
engine::getMixer()->checkValidityOfPlayHandles();
|
||||
|
||||
m_trackType = INSTRUMENT_TRACK;
|
||||
engine::getMixer()->removePlayHandles( this );
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -59,6 +59,7 @@
|
||||
#include "templates.h"
|
||||
#include "gui_templates.h"
|
||||
#include "embed.h"
|
||||
#include "engine.h"
|
||||
#include "piano_roll.h"
|
||||
#include "track_container.h"
|
||||
#include "rename_dialog.h"
|
||||
@@ -87,8 +88,6 @@ pattern::pattern ( instrumentTrack * _instrument_track ) :
|
||||
m_patternType( BEAT_PATTERN ),
|
||||
m_name( _instrument_track->name() ),
|
||||
m_steps( DEFAULT_STEPS_PER_TACT ),
|
||||
//TODO: check mutex
|
||||
m_frozenPatternMutex(),
|
||||
m_frozenPattern( NULL ),
|
||||
m_freezing( FALSE ),
|
||||
m_freezeAborted( FALSE )
|
||||
@@ -107,7 +106,6 @@ pattern::pattern( const pattern & _pat_to_copy ) :
|
||||
m_patternType( _pat_to_copy.m_patternType ),
|
||||
m_name( "" ),
|
||||
m_steps( _pat_to_copy.m_steps ),
|
||||
m_frozenPatternMutex(),
|
||||
m_frozenPattern( NULL ),
|
||||
m_freezeAborted( FALSE )
|
||||
{
|
||||
@@ -146,12 +144,10 @@ pattern::~pattern()
|
||||
|
||||
m_notes.clear();
|
||||
|
||||
m_frozenPatternMutex.lock();
|
||||
if( m_frozenPattern )
|
||||
{
|
||||
sharedObject::unref( m_frozenPattern );
|
||||
}
|
||||
m_frozenPatternMutex.unlock();
|
||||
}
|
||||
|
||||
|
||||
@@ -250,6 +246,7 @@ note * pattern::addNote( const note & _new_note, const bool _quant_pos )
|
||||
new_note->quantizePos( engine::getPianoRoll()->quantization() );
|
||||
}
|
||||
|
||||
engine::getMixer()->lock();
|
||||
if( m_notes.size() == 0 || m_notes.back()->pos() <= new_note->pos() )
|
||||
{
|
||||
m_notes.push_back( new_note );
|
||||
@@ -272,6 +269,7 @@ note * pattern::addNote( const note & _new_note, const bool _quant_pos )
|
||||
|
||||
m_notes.insert( it, new_note );
|
||||
}
|
||||
engine::getMixer()->unlock();
|
||||
|
||||
checkType();
|
||||
update();
|
||||
@@ -287,6 +285,7 @@ note * pattern::addNote( const note & _new_note, const bool _quant_pos )
|
||||
|
||||
void pattern::removeNote( const note * _note_to_del )
|
||||
{
|
||||
engine::getMixer()->lock();
|
||||
noteVector::iterator it = m_notes.begin();
|
||||
while( it != m_notes.end() )
|
||||
{
|
||||
@@ -298,6 +297,7 @@ void pattern::removeNote( const note * _note_to_del )
|
||||
}
|
||||
++it;
|
||||
}
|
||||
engine::getMixer()->unlock();
|
||||
|
||||
checkType();
|
||||
update();
|
||||
@@ -325,13 +325,15 @@ note * pattern::rearrangeNote( const note * _note_to_proc,
|
||||
|
||||
void pattern::clearNotes( void )
|
||||
{
|
||||
engine::getMixer()->lock();
|
||||
for( noteVector::iterator it = m_notes.begin(); it != m_notes.end();
|
||||
++it )
|
||||
{
|
||||
delete *it;
|
||||
}
|
||||
|
||||
m_notes.clear();
|
||||
engine::getMixer()->unlock();
|
||||
|
||||
checkType();
|
||||
update();
|
||||
if( engine::getPianoRoll()->currentPattern() == this )
|
||||
@@ -343,32 +345,6 @@ void pattern::clearNotes( void )
|
||||
|
||||
|
||||
|
||||
note * pattern::noteAt( int _note_num )
|
||||
{
|
||||
if( (csize) _note_num < m_notes.size() )
|
||||
{
|
||||
return( m_notes[_note_num] );
|
||||
}
|
||||
return( NULL );
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
void pattern::setNoteAt( int _note_num, note _new_note )
|
||||
{
|
||||
if( static_cast<csize>( _note_num ) < m_notes.size() )
|
||||
{
|
||||
delete m_notes[_note_num];
|
||||
m_notes[_note_num] = new note( _new_note );
|
||||
checkType();
|
||||
update();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
void pattern::setType( patternTypes _new_pattern_type )
|
||||
{
|
||||
if( _new_pattern_type == BEAT_PATTERN ||
|
||||
@@ -597,10 +573,8 @@ void pattern::unfreeze( void )
|
||||
{
|
||||
if( m_frozenPattern != NULL )
|
||||
{
|
||||
m_frozenPatternMutex.lock();
|
||||
sharedObject::unref( m_frozenPattern );
|
||||
m_frozenPattern = NULL;
|
||||
m_frozenPatternMutex.unlock();
|
||||
update();
|
||||
}
|
||||
}
|
||||
@@ -1069,7 +1043,7 @@ void pattern::paintEvent( QPaintEvent * )
|
||||
for( noteVector::iterator it = m_notes.begin();
|
||||
it != m_notes.end(); ++it )
|
||||
{
|
||||
Sint16 no = it - m_notes.begin();
|
||||
Sint16 no = ( *it )->pos() / 4;
|
||||
Sint16 x = TCO_BORDER_WIDTH + static_cast<int>( no *
|
||||
w / steps );
|
||||
Sint16 y = height() - s_stepBtnOff->height() - 1;
|
||||
@@ -1348,6 +1322,13 @@ void patternFreezeThread::run( void )
|
||||
freeze_recorder->processNextBuffer();
|
||||
m_statusDlg->setProgress( ppp * 100 / m_pattern->length() );
|
||||
}
|
||||
m_statusDlg->setProgress( 100 );
|
||||
// render tails
|
||||
while( engine::getMixer()->hasPlayHandles() &&
|
||||
m_pattern->m_freezeAborted == FALSE )
|
||||
{
|
||||
freeze_recorder->processNextBuffer();
|
||||
}
|
||||
|
||||
|
||||
m_pattern->m_freezing = FALSE;
|
||||
@@ -1359,10 +1340,8 @@ void patternFreezeThread::run( void )
|
||||
// create final sample-buffer if freezing was successful
|
||||
if( m_pattern->m_freezeAborted == FALSE )
|
||||
{
|
||||
m_pattern->m_frozenPatternMutex.lock();
|
||||
freeze_recorder->createSampleBuffer(
|
||||
&m_pattern->m_frozenPattern );
|
||||
m_pattern->m_frozenPatternMutex.unlock();
|
||||
}
|
||||
|
||||
// restore original audio-device
|
||||
|
||||
@@ -56,8 +56,8 @@
|
||||
#include "automation_pattern.h"
|
||||
#include "sample_play_handle.h"
|
||||
#include "string_pair_drag.h"
|
||||
#include "knob.h"
|
||||
#include "volume.h"
|
||||
#include "volume_knob.h"
|
||||
|
||||
|
||||
sampleTCO::sampleTCO( track * _track ) :
|
||||
@@ -402,6 +402,7 @@ sampleTrack::sampleTrack( trackContainer * _tc ) :
|
||||
|
||||
sampleTrack::~sampleTrack()
|
||||
{
|
||||
engine::getMixer()->removePlayHandles( this );
|
||||
delete m_audioPort;
|
||||
}
|
||||
|
||||
@@ -509,24 +510,7 @@ void sampleTrack::loadTrackSpecificSettings( const QDomElement & _this )
|
||||
m_trackLabel->setPixmapFile( _this.attribute( "icon" ) );
|
||||
}
|
||||
#endif
|
||||
if( _this.attribute( "vol" ) != "" )
|
||||
{
|
||||
m_volumeKnob->setInitValue( _this.attribute( "vol" ).toFloat()
|
||||
* 100.0f );
|
||||
}
|
||||
else
|
||||
{
|
||||
QDomNode node = _this.namedItem(
|
||||
automationPattern::classNodeName() );
|
||||
if( node.isElement() && node.namedItem( "vol" ).isElement() )
|
||||
{
|
||||
m_volumeKnob->loadSettings( _this, "vol" );
|
||||
}
|
||||
else
|
||||
{
|
||||
m_volumeKnob->setInitValue( 100.0f );
|
||||
}
|
||||
}
|
||||
m_volumeKnob->loadSettings( _this, "vol" );
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -44,6 +44,7 @@
|
||||
|
||||
#include "automatable_object_templates.h"
|
||||
#include "embed.h"
|
||||
#include "knob.h"
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -27,6 +27,18 @@
|
||||
|
||||
|
||||
#include "effect_label.h"
|
||||
|
||||
#ifndef QT3
|
||||
|
||||
#include <QtXml/QDomElement>
|
||||
|
||||
#else
|
||||
|
||||
#include <qdom.h>
|
||||
|
||||
#endif
|
||||
|
||||
#include "effect_tab_widget.h"
|
||||
#include "sample_track.h"
|
||||
#include "embed.h"
|
||||
#include "engine.h"
|
||||
@@ -74,6 +86,15 @@ effectLabel::effectLabel( const QString & _initial_name, QWidget * _parent,
|
||||
|
||||
effectLabel::~effectLabel()
|
||||
{
|
||||
delete m_effWidget;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
QString effectLabel::text( void ) const
|
||||
{
|
||||
return( m_label->text() );
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -30,17 +30,21 @@
|
||||
#ifdef QT4
|
||||
|
||||
#include <QtCore/QTimer>
|
||||
#include <QtGui/QApplication>
|
||||
#include <QtGui/QPainter>
|
||||
#include <QtGui/QPixmap>
|
||||
|
||||
#else
|
||||
|
||||
#include <qapplication.h>
|
||||
#include <qtimer.h>
|
||||
#include <qpainter.h>
|
||||
#include <qpixmap.h>
|
||||
|
||||
#endif
|
||||
|
||||
#include "update_event.h"
|
||||
|
||||
|
||||
fadeButton::fadeButton( const QColor & _normal_color,
|
||||
const QColor & _activated_color, QWidget * _parent ) :
|
||||
@@ -52,7 +56,6 @@ fadeButton::fadeButton( const QColor & _normal_color,
|
||||
#ifndef QT4
|
||||
setBackgroundMode( NoBackground );
|
||||
#endif
|
||||
QTimer::singleShot( 20, this, SLOT( nextState( void ) ) );
|
||||
}
|
||||
|
||||
|
||||
@@ -68,7 +71,7 @@ fadeButton::~fadeButton()
|
||||
void fadeButton::activate( void )
|
||||
{
|
||||
m_state = 1.00f;
|
||||
update();
|
||||
signalUpdate();
|
||||
}
|
||||
|
||||
|
||||
@@ -76,13 +79,25 @@ void fadeButton::activate( void )
|
||||
void fadeButton::reset( void )
|
||||
{
|
||||
m_state = 0.0f;
|
||||
update();
|
||||
signalUpdate();
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
#ifndef QT3
|
||||
void fadeButton::customEvent( QEvent * )
|
||||
#else
|
||||
void fadeButton::customEvent( QCustomEvent * )
|
||||
#endif
|
||||
{
|
||||
update();
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
void fadeButton::paintEvent( QPaintEvent * _pe )
|
||||
{
|
||||
QColor col = m_normalColor;
|
||||
@@ -98,6 +113,9 @@ void fadeButton::paintEvent( QPaintEvent * _pe )
|
||||
( 1.0f - m_state ) +
|
||||
m_activatedColor.blue() * m_state );
|
||||
col.setRgb( r, g, b );
|
||||
|
||||
m_state -= 0.1f;
|
||||
QTimer::singleShot( 20, this, SLOT( update() ) );
|
||||
}
|
||||
#ifdef QT4
|
||||
QPainter p( this );
|
||||
@@ -123,14 +141,9 @@ void fadeButton::paintEvent( QPaintEvent * _pe )
|
||||
|
||||
|
||||
|
||||
void fadeButton::nextState( void )
|
||||
void fadeButton::signalUpdate( void )
|
||||
{
|
||||
if( m_state > 0.0f )
|
||||
{
|
||||
m_state -= 0.1f;
|
||||
update();
|
||||
}
|
||||
QTimer::singleShot( 20, this, SLOT( nextState( void ) ) );
|
||||
QApplication::postEvent( this, new updateEvent() );
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -137,6 +137,7 @@ knob::knob( int _knob_num, QWidget * _parent, const QString & _name,
|
||||
// Destructor
|
||||
knob::~knob()
|
||||
{
|
||||
delete m_knobPixmap;
|
||||
/* // make sure pointer to this knob isn't used anymore in active
|
||||
// midi-device-class
|
||||
if( engine::getMixer()->getMIDIClient()->pitchBendKnob() == this )
|
||||
@@ -251,7 +252,7 @@ void knob::valueChange( void )
|
||||
recalcAngle();
|
||||
update();
|
||||
emit valueChanged( value() );
|
||||
emit valueChanged( dynamic_cast<autoObj *>( this )->data() );
|
||||
emit valueChanged();
|
||||
}
|
||||
|
||||
|
||||
@@ -492,7 +493,7 @@ void knob::mouseMoveEvent( QMouseEvent * _me )
|
||||
{
|
||||
setPosition( _me->pos() );
|
||||
emit sliderMoved( value() );
|
||||
emit valueChanged( dynamic_cast<autoObj *>( this )->data() );
|
||||
emit valueChanged();
|
||||
if( !configManager::inst()->value( "knobs",
|
||||
"classicalusability").toInt() )
|
||||
{
|
||||
@@ -606,7 +607,7 @@ void knob::wheelEvent( QWheelEvent * _we )
|
||||
s_textFloat->setVisibilityTimeOut( 1000 );
|
||||
|
||||
emit sliderMoved( value() );
|
||||
emit valueChanged( dynamic_cast<autoObj *>( this )->data() );
|
||||
emit valueChanged();
|
||||
}
|
||||
|
||||
|
||||
@@ -615,7 +616,7 @@ void knob::wheelEvent( QWheelEvent * _we )
|
||||
void knob::buttonReleased( void )
|
||||
{
|
||||
emit valueChanged( value() );
|
||||
emit valueChanged( dynamic_cast<autoObj *>( this )->data() );
|
||||
emit valueChanged();
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -54,7 +54,9 @@
|
||||
#endif
|
||||
|
||||
#include "rack_plugin.h"
|
||||
#include "audio_port.h"
|
||||
#include "knob.h"
|
||||
#include "led_checkbox.h"
|
||||
#include "tempo_sync_knob.h"
|
||||
#include "tooltip.h"
|
||||
#include "effect_control_dialog.h"
|
||||
@@ -72,11 +74,8 @@ rackPlugin::rackPlugin( QWidget * _parent,
|
||||
m_effect( _eff ),
|
||||
m_track( _track ),
|
||||
m_port( _port ),
|
||||
m_contextMenu( NULL ),
|
||||
m_show( TRUE )
|
||||
{
|
||||
m_port->getEffects()->appendEffect( m_effect );
|
||||
|
||||
setFixedSize( 210, 60 );
|
||||
|
||||
QPixmap bg = embed::getIconPixmap( "effect_plugin" );
|
||||
@@ -228,12 +227,15 @@ rackPlugin::rackPlugin( QWidget * _parent,
|
||||
|
||||
"Right clicking will bring up a context menu where you can change the order "
|
||||
"in which the effects are processed or delete an effect altogether." ) );
|
||||
|
||||
m_port->getEffects()->appendEffect( m_effect );
|
||||
}
|
||||
|
||||
|
||||
|
||||
rackPlugin::~rackPlugin()
|
||||
{
|
||||
m_port->getEffects()->removeEffect( m_effect );
|
||||
delete m_effect;
|
||||
m_controlView->deleteLater();
|
||||
}
|
||||
@@ -293,9 +295,9 @@ void rackPlugin::setGate( float _value )
|
||||
|
||||
void rackPlugin::contextMenuEvent( QContextMenuEvent * )
|
||||
{
|
||||
m_contextMenu = new QMenu( this );
|
||||
QPointer<QMenu> contextMenu = new QMenu( this );
|
||||
#ifdef QT4
|
||||
m_contextMenu->setTitle( m_effect->publicName() );
|
||||
contextMenu->setTitle( m_effect->publicName() );
|
||||
#else
|
||||
QLabel * caption = new QLabel( "<font color=white><b>" +
|
||||
QString( m_effect->publicName() ) +
|
||||
@@ -303,27 +305,24 @@ void rackPlugin::contextMenuEvent( QContextMenuEvent * )
|
||||
this );
|
||||
caption->setPaletteBackgroundColor( QColor( 0, 0, 192 ) );
|
||||
caption->setAlignment( Qt::AlignCenter );
|
||||
m_contextMenu->addAction( caption );
|
||||
contextMenu->addAction( caption );
|
||||
#endif
|
||||
m_contextMenu->addAction( embed::getIconPixmap( "arp_up_on" ),
|
||||
contextMenu->addAction( embed::getIconPixmap( "arp_up_on" ),
|
||||
tr( "Move &up" ),
|
||||
this, SLOT( moveUp() ) );
|
||||
m_contextMenu->addAction( embed::getIconPixmap( "arp_down_on" ),
|
||||
contextMenu->addAction( embed::getIconPixmap( "arp_down_on" ),
|
||||
tr( "Move &down" ),
|
||||
this, SLOT( moveDown() ) );
|
||||
m_contextMenu->addSeparator();
|
||||
m_contextMenu->addAction( embed::getIconPixmap( "cancel" ),
|
||||
contextMenu->addSeparator();
|
||||
contextMenu->addAction( embed::getIconPixmap( "cancel" ),
|
||||
tr( "&Remove this plugin" ),
|
||||
this, SLOT( deletePlugin() ) );
|
||||
m_contextMenu->addSeparator();
|
||||
m_contextMenu->addAction( embed::getIconPixmap( "help" ),
|
||||
contextMenu->addSeparator();
|
||||
contextMenu->addAction( embed::getIconPixmap( "help" ),
|
||||
tr( "&Help" ),
|
||||
this, SLOT( displayHelp() ) );
|
||||
m_contextMenu->exec( QCursor::pos() );
|
||||
if( m_contextMenu != NULL )
|
||||
{
|
||||
delete m_contextMenu;
|
||||
}
|
||||
contextMenu->exec( QCursor::pos() );
|
||||
delete contextMenu;
|
||||
}
|
||||
|
||||
|
||||
@@ -331,11 +330,6 @@ void rackPlugin::contextMenuEvent( QContextMenuEvent * )
|
||||
|
||||
void rackPlugin::moveUp()
|
||||
{
|
||||
if( m_contextMenu != NULL )
|
||||
{
|
||||
delete m_contextMenu;
|
||||
m_contextMenu = NULL;
|
||||
}
|
||||
emit( moveUp( this ) );
|
||||
}
|
||||
|
||||
@@ -344,11 +338,6 @@ void rackPlugin::moveUp()
|
||||
|
||||
void rackPlugin::moveDown()
|
||||
{
|
||||
if( m_contextMenu != NULL )
|
||||
{
|
||||
delete m_contextMenu;
|
||||
m_contextMenu = NULL;
|
||||
}
|
||||
emit( moveDown( this ) );
|
||||
}
|
||||
|
||||
@@ -356,11 +345,6 @@ void rackPlugin::moveDown()
|
||||
|
||||
void rackPlugin::deletePlugin()
|
||||
{
|
||||
if( m_contextMenu != NULL )
|
||||
{
|
||||
delete m_contextMenu;
|
||||
m_contextMenu = NULL;
|
||||
}
|
||||
emit( deletePlugin( this ) );
|
||||
}
|
||||
|
||||
|
||||
@@ -39,6 +39,8 @@
|
||||
|
||||
|
||||
#include "rack_view.h"
|
||||
#include "audio_port.h"
|
||||
#include "rack_plugin.h"
|
||||
|
||||
|
||||
rackView::rackView( QWidget * _parent, track * _track, audioPort * _port ) :
|
||||
@@ -68,6 +70,12 @@ rackView::rackView( QWidget * _parent, track * _track, audioPort * _port ) :
|
||||
|
||||
rackView::~rackView()
|
||||
{
|
||||
for( vvector<rackPlugin *>::iterator it = m_rackInserts.begin();
|
||||
it != m_rackInserts.end(); )
|
||||
{
|
||||
delete *it;
|
||||
m_rackInserts.erase( it );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -169,29 +177,14 @@ void rackView::moveDown( rackPlugin * _plugin )
|
||||
|
||||
void rackView::deletePlugin( rackPlugin * _plugin )
|
||||
{
|
||||
m_port->getEffects()->deleteEffect( _plugin->getEffect() );
|
||||
|
||||
#ifdef QT3
|
||||
m_scrollArea->removeChild( _plugin );
|
||||
#endif
|
||||
|
||||
vvector<rackPlugin *>::iterator loc = NULL;
|
||||
for( vvector<rackPlugin *>::iterator it = m_rackInserts.begin();
|
||||
it != m_rackInserts.end(); it++ )
|
||||
{
|
||||
if( *it == _plugin )
|
||||
{
|
||||
loc = it;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if( loc != NULL )
|
||||
{
|
||||
delete _plugin;
|
||||
m_rackInserts.erase( loc );
|
||||
redraw();
|
||||
}
|
||||
m_rackInserts.erase( qFind( m_rackInserts.begin(), m_rackInserts.end(),
|
||||
_plugin ) );
|
||||
delete _plugin;
|
||||
redraw();
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -48,9 +48,10 @@
|
||||
|
||||
#include "tempo_sync_knob.h"
|
||||
#include "automatable_object_templates.h"
|
||||
#include "song_editor.h"
|
||||
#include "embed.h"
|
||||
#include "main_window.h"
|
||||
#include "meter_dialog.h"
|
||||
#include "song_editor.h"
|
||||
|
||||
|
||||
tempoSyncKnob::tempoSyncKnob( int _knob_num, QWidget * _parent,
|
||||
|
||||
@@ -131,7 +131,7 @@ void volumeKnob::mouseMoveEvent( QMouseEvent * _me )
|
||||
{
|
||||
setPosition( _me->pos() );
|
||||
emit sliderMoved( value() );
|
||||
emit valueChanged( dynamic_cast<autoObj *>( this )->data() );
|
||||
emit valueChanged();
|
||||
if( !configManager::inst()->value( "knobs",
|
||||
"classicalusability").toInt() )
|
||||
{
|
||||
@@ -183,7 +183,7 @@ void volumeKnob::wheelEvent( QWheelEvent * _we )
|
||||
s_textFloat->setVisibilityTimeOut( 1000 );
|
||||
|
||||
emit sliderMoved( value() );
|
||||
emit valueChanged( dynamic_cast<autoObj *>( this )->data() );
|
||||
emit valueChanged();
|
||||
}
|
||||
|
||||
|
||||
|
||||
Reference in New Issue
Block a user