@@ -492,6 +492,7 @@ Audio_Region::draw ( void ) | |||||
/* no coverage */ | /* no coverage */ | ||||
return; | return; | ||||
if ( start() > timeline->xoffset + timeline->x_to_ts( sequence()->w() ) || | if ( start() > timeline->xoffset + timeline->x_to_ts( sequence()->w() ) || | ||||
start() + length() < timeline->xoffset ) | start() + length() < timeline->xoffset ) | ||||
/* not in viewport */ | /* not in viewport */ | ||||
@@ -499,31 +500,31 @@ Audio_Region::draw ( void ) | |||||
fl_push_clip( X, Y, W, H ); | fl_push_clip( X, Y, W, H ); | ||||
/* account for waveform outlines... */ | |||||
X -= 2; | |||||
W += 4; | |||||
/* overdraw a little to avoid artifacts when scrolling */ | |||||
W += 2; | |||||
Fl_Color c = selected() ? fl_invert_color( _color ) : _color; | Fl_Color c = selected() ? fl_invert_color( _color ) : _color; | ||||
/* start with region length... */ | |||||
// int rw = timeline->ts_to_x( min( length(), timeline->x_to_ts( sequence()->w() ) ) ); | |||||
int rw = W; | |||||
/* calculate waveform offset due to scrolling */ | |||||
nframes_t offset = 0; | |||||
if ( start() < timeline->xoffset ) | |||||
if ( sequence()->damage() & FL_DAMAGE_USER1 && this == sequence()->track()->capture_region() ) | |||||
{ | { | ||||
offset = timeline->xoffset - start(); | |||||
/* just draw the section with the updated peaks... */ | |||||
// rw -= timeline->ts_to_x( offset ); | |||||
nframes_t absolute_frame = _r->start + sequence()->track()->capture()->last_frame_drawn; | |||||
int nx = sequence()->x() + timeline->ts_to_x( absolute_frame - scroll_ts() ); | |||||
W -= nx - X; | |||||
X = nx; | |||||
} | } | ||||
/* DMESSAGE( "rw = %d", rw ); */ | |||||
const int rx = x(); | |||||
/* calculate waveform offset due to scrolling */ | |||||
/* offset is the number of frames into the waveform the value of X translates to */ | |||||
nframes_t x_frame = timeline->xoffset + timeline->x_to_ts( X - _sequence->x() ); | |||||
nframes_t offset = x_frame - start(); | |||||
/* fl_color( FL_RED ); */ | |||||
/* fl_line( rx + rw, y(), rx + rw, y() + h() ); */ | |||||
nframes_t fo = 0; | |||||
nframes_t ostart = 0, oend = 0; | |||||
const int total_peaks_needed = W; | |||||
nframes_t total_frames_needed = timeline->x_to_ts( total_peaks_needed ); | |||||
{ | { | ||||
Fl_Color c = fl_color_average( FL_DARK1, | Fl_Color c = fl_color_average( FL_DARK1, | ||||
@@ -536,38 +537,27 @@ Audio_Region::draw ( void ) | |||||
draw_fade( _fade_out, Fade::Out, false, X, W ); | draw_fade( _fade_out, Fade::Out, false, X, W ); | ||||
} | } | ||||
int xo = 0; | |||||
nframes_t ostart = 0, oend = 0; | |||||
const int total_peaks_needed = rw; | |||||
int channels = 0; | |||||
int peaks = 0; | |||||
Peak *pbuf = NULL; | |||||
/* compensate for scrolling */ | |||||
if ( X - rx > 0 ) | |||||
offset += timeline->x_to_ts( X - rx ); | |||||
// DMESSAGE( "Drawing audio region."); | |||||
int channels; | |||||
int peaks; | |||||
Peak *pbuf = NULL; | |||||
do { | do { | ||||
nframes_t start = _r->offset; | nframes_t start = _r->offset; | ||||
int loop_peaks_needed = _loop ? timeline->ts_to_x( _loop ) : timeline->ts_to_x( _clip->length() ); | |||||
nframes_t loop_frames_needed = _loop ? _loop : total_frames_needed; | |||||
int loop_peaks_needed = timeline->ts_to_x( loop_frames_needed ); | |||||
Fl_Color c = Fl::get_color( _color ); | |||||
if ( this == ((Audio_Sequence*)sequence())->capture_region() ) | if ( this == ((Audio_Sequence*)sequence())->capture_region() ) | ||||
{ | { | ||||
loop_peaks_needed = timeline->ts_to_x( _range.length ); | |||||
// loop_peaks_needed = timeline->ts_to_x( _range.length ); | |||||
c = FL_BLACK; | c = FL_BLACK; | ||||
} | } | ||||
c = fl_color_add_alpha( c, 220 ); | |||||
if ( ! loop_peaks_needed ) | |||||
break; | |||||
if ( ! xo ) /* first loop... */ | |||||
if ( ! fo ) /* first loop... */ | |||||
{ | { | ||||
if ( _loop ) | if ( _loop ) | ||||
start += offset % _loop; | start += offset % _loop; | ||||
@@ -577,38 +567,38 @@ Audio_Region::draw ( void ) | |||||
/* DMESSAGE( "offset = %lu", (unsigned long) offset ); */ | /* DMESSAGE( "offset = %lu", (unsigned long) offset ); */ | ||||
/* DMESSAGE( "loop peaks needed = %d", loop_peaks_needed ); */ | /* DMESSAGE( "loop peaks needed = %d", loop_peaks_needed ); */ | ||||
loop_peaks_needed -= timeline->ts_to_x( offset % timeline->x_to_ts( loop_peaks_needed ) ); | |||||
loop_peaks_needed = min( loop_peaks_needed, total_peaks_needed ); | |||||
if ( _loop ) | |||||
{ | |||||
loop_frames_needed -= offset % loop_frames_needed; | |||||
loop_peaks_needed = timeline->ts_to_x( loop_frames_needed ); | |||||
} | |||||
/* DMESSAGE( "loop peaks needed = %d", loop_peaks_needed ); */ | /* DMESSAGE( "loop peaks needed = %d", loop_peaks_needed ); */ | ||||
assert( loop_peaks_needed >= 0 ); | assert( loop_peaks_needed >= 0 ); | ||||
} | } | ||||
if ( xo + loop_peaks_needed > total_peaks_needed ) | |||||
if ( fo + loop_frames_needed > total_frames_needed ) | |||||
{ | { | ||||
loop_peaks_needed -= ( xo + loop_peaks_needed ) - total_peaks_needed; | |||||
loop_frames_needed -= ( fo + loop_frames_needed ) - total_frames_needed; | |||||
loop_peaks_needed = timeline->ts_to_x( loop_frames_needed ); | |||||
} | } | ||||
if ( 0 == loop_peaks_needed ) | |||||
if ( !loop_peaks_needed ) | |||||
break; | break; | ||||
const nframes_t end = start + timeline->x_to_ts( loop_peaks_needed ); | |||||
const nframes_t end = start + loop_frames_needed; | |||||
if ( start != ostart || end != oend ) | if ( start != ostart || end != oend ) | ||||
{ | { | ||||
if ( _clip->peaks()->peakfile_ready() ) | if ( _clip->peaks()->peakfile_ready() ) | ||||
{ | { | ||||
if ( _clip->read_peaks( timeline->fpp(), | if ( _clip->read_peaks( timeline->fpp(), | ||||
start, | |||||
end, | |||||
start, | |||||
end, | |||||
&peaks, &pbuf, &channels ) ) | &peaks, &pbuf, &channels ) ) | ||||
{ | { | ||||
Waveform::scale( pbuf, peaks * channels, _scale ); | Waveform::scale( pbuf, peaks * channels, _scale ); | ||||
ostart = start; | ostart = start; | ||||
oend = end; | oend = end; | ||||
} | } | ||||
@@ -626,14 +616,11 @@ Audio_Region::draw ( void ) | |||||
{ | { | ||||
// DMESSAGE( "using cached peaks" ); | // DMESSAGE( "using cached peaks" ); | ||||
} | } | ||||
Fl_Color c = Fl::get_color( _color ); | |||||
c = fl_color_add_alpha( c, 220 ); | |||||
if ( peaks && pbuf ) | if ( peaks && pbuf ) | ||||
{ | { | ||||
int ch = (h() - Fl::box_dh( box() )) / channels; | int ch = (h() - Fl::box_dh( box() )) / channels; | ||||
int xo = timeline->ts_to_x( fo ); | |||||
for ( int i = 0; i < channels; ++i ) | for ( int i = 0; i < channels; ++i ) | ||||
{ | { | ||||
@@ -645,26 +632,31 @@ Audio_Region::draw ( void ) | |||||
c ); | c ); | ||||
} | } | ||||
} | } | ||||
else | |||||
WARNING( "Pbuf == %p, peaks = %lu", pbuf, (unsigned long)peaks ); | |||||
if ( sequence()->damage() & FL_DAMAGE_USER1 && this == sequence()->track()->capture_region() ) | |||||
sequence()->track()->capture()->last_frame_drawn = start + peaks; | |||||
if ( peaks < loop_peaks_needed ) | if ( peaks < loop_peaks_needed ) | ||||
{ | { | ||||
// DMESSAGE( "Peak read came up %lu peaks short", (unsigned long) loop_peaks_needed - peaks ); | |||||
DMESSAGE( "Peak read came up %lu peaks short", (unsigned long)loop_peaks_needed - peaks ); | |||||
} | } | ||||
xo += loop_peaks_needed; | |||||
fo += loop_frames_needed; | |||||
} | } | ||||
while ( _loop && xo < W ); | |||||
while ( _loop && fo < total_frames_needed ); | |||||
if ( _loop && offset < _loop ) | if ( _loop && offset < _loop ) | ||||
{ | { | ||||
const int lx = timeline->ts_to_x( _loop - offset ); | |||||
const int lx = get_x( start() + _loop ); | |||||
if ( lx < X + W ) | if ( lx < X + W ) | ||||
{ | { | ||||
fl_color( FL_RED ); | fl_color( FL_RED ); | ||||
fl_line_style( FL_DASH, 0 ); | fl_line_style( FL_DASH, 0 ); | ||||
fl_line( X + lx + 2, y(), X + lx + 2, y() + h() ); | |||||
fl_line( lx, y(), lx, y() + h() ); | |||||
fl_line_style( FL_SOLID, 0 ); | fl_line_style( FL_SOLID, 0 ); | ||||
} | } | ||||
} | } | ||||
@@ -689,12 +681,6 @@ Audio_Region::draw ( void ) | |||||
fl_line_style( FL_SOLID, 0 ); | fl_line_style( FL_SOLID, 0 ); | ||||
} | } | ||||
/* fl_color( FL_BLACK ); */ | |||||
/* fl_line( rx, Y, rx, Y + H ); */ | |||||
/* fl_line( rx + rw - 1, Y, rx + rw - 1, Y + H ); */ | |||||
/* if ( current() ) */ | /* if ( current() ) */ | ||||
/* { */ | /* { */ | ||||
/* /\* draw length bubble *\/ */ | /* /\* draw length bubble *\/ */ | ||||
@@ -147,22 +147,14 @@ Audio_File::release ( void ) | |||||
bool | bool | ||||
Audio_File::read_peaks( float fpp, nframes_t start, nframes_t end, int *peaks, Peak **pbuf, int *channels ) | Audio_File::read_peaks( float fpp, nframes_t start, nframes_t end, int *peaks, Peak **pbuf, int *channels ) | ||||
{ | { | ||||
// Peaks pk; | |||||
*peaks = 0; | |||||
*channels = 0; | |||||
*pbuf = NULL; | |||||
if ( dummy() ) | if ( dummy() ) | ||||
{ | |||||
*peaks = (end - start) / fpp; | |||||
*channels = 0; | |||||
*pbuf = NULL; | |||||
return false; | return false; | ||||
} | |||||
else | else | ||||
{ | { | ||||
*peaks = 0; | |||||
*channels = 0; | |||||
*pbuf = NULL; | |||||
*peaks = _peaks.fill_buffer( fpp, start, end ); | *peaks = _peaks.fill_buffer( fpp, start, end ); | ||||
*channels = this->channels(); | *channels = this->channels(); | ||||
@@ -40,7 +40,7 @@ public: | |||||
bool open ( void ) { return true; } | bool open ( void ) { return true; } | ||||
void close ( void ) { } | void close ( void ) { } | ||||
void seek ( nframes_t ) { } | void seek ( nframes_t ) { } | ||||
nframes_t read ( sample_t *, int, nframes_t len ) { return len; } | |||||
nframes_t read ( sample_t *, int, nframes_t start, nframes_t end ) { return end - start; } | |||||
nframes_t read ( sample_t *, int, nframes_t len ) { return 0; } | |||||
nframes_t read ( sample_t *, int, nframes_t start, nframes_t end ) { return 0; } | |||||
nframes_t write ( sample_t *, nframes_t nframes ) { return nframes; } | nframes_t write ( sample_t *, nframes_t nframes ) { return nframes; } | ||||
}; | }; |
@@ -242,13 +242,13 @@ Audio_File_SF::write ( sample_t *buf, nframes_t nframes ) | |||||
{ | { | ||||
_peaks.write( buf, nframes ); | _peaks.write( buf, nframes ); | ||||
// lock(); | |||||
lock(); | |||||
nframes_t l = sf_writef_float( _in, buf, nframes ); | nframes_t l = sf_writef_float( _in, buf, nframes ); | ||||
_length += l; | _length += l; | ||||
// unlock(); | |||||
unlock(); | |||||
return l; | return l; | ||||
} | } |
@@ -83,7 +83,7 @@ Audio_Region::read ( sample_t *buf, nframes_t pos, nframes_t nframes, int channe | |||||
nframes_t sofs, /* offset into source */ | nframes_t sofs, /* offset into source */ | ||||
ofs, /* offset into buffer */ | ofs, /* offset into buffer */ | ||||
cnt; | |||||
cnt; /* number of frames to read */ | |||||
cnt = nframes; | cnt = nframes; | ||||
@@ -105,8 +105,8 @@ Audio_Region::read ( sample_t *buf, nframes_t pos, nframes_t nframes, int channe | |||||
return 0; | return 0; | ||||
// const nframes_t start = ofs + r.start + sofs; | // const nframes_t start = ofs + r.start + sofs; | ||||
const nframes_t start = r.offset + sofs; | |||||
const nframes_t len = min( cnt, nframes - ofs ); | |||||
const nframes_t start = r.offset + sofs; | |||||
const nframes_t len = cnt; | |||||
if ( len == 0 ) | if ( len == 0 ) | ||||
return 0; | return 0; | ||||
@@ -139,6 +139,9 @@ Audio_Region::read ( sample_t *buf, nframes_t pos, nframes_t nframes, int channe | |||||
else | else | ||||
cnt = _clip->read( buf + ofs, channel, start, len ); | cnt = _clip->read( buf + ofs, channel, start, len ); | ||||
if ( ! cnt ) | |||||
return 0; | |||||
/* apply gain */ | /* apply gain */ | ||||
buffer_apply_gain( buf + ofs, cnt, _scale ); | buffer_apply_gain( buf + ofs, cnt, _scale ); | ||||
@@ -194,9 +197,7 @@ Audio_Region::write ( nframes_t nframes ) | |||||
if ( W ) | if ( W ) | ||||
{ | { | ||||
Fl::lock(); | Fl::lock(); | ||||
// sequence()->damage( FL_DAMAGE_ALL, ( x() + w() - W ) - 20, y(), W, h() ); | |||||
sequence()->damage( FL_DAMAGE_ALL, x(), y(), w(), h() ); | |||||
// Fl::awake(); | |||||
sequence()->damage(FL_DAMAGE_USER1, x(), y(), w(), h()); | |||||
Fl::unlock(); | Fl::unlock(); | ||||
} | } | ||||
} | } | ||||
@@ -104,7 +104,7 @@ class Peakfile | |||||
FILE *_fp; | FILE *_fp; | ||||
nframes_t _chunksize; | nframes_t _chunksize; | ||||
int _channels; /* number of channels this peakfile represents */ | int _channels; /* number of channels this peakfile represents */ | ||||
nframes_t _length; /* length, in frames, of the clip this peakfile represents */ | |||||
// nframes_t _length; /* length, in frames, of the clip this peakfile represents */ | |||||
off_t _offset; | off_t _offset; | ||||
// int _blocks; | // int _blocks; | ||||
@@ -134,7 +134,7 @@ public: | |||||
_offset = 0; | _offset = 0; | ||||
_chunksize = 0; | _chunksize = 0; | ||||
_channels = 0; | _channels = 0; | ||||
_length = 0; | |||||
// _length = 0; | |||||
} | } | ||||
~Peakfile ( ) | ~Peakfile ( ) | ||||
@@ -163,7 +163,7 @@ public: | |||||
if ( feof( _fp ) ) | if ( feof( _fp ) ) | ||||
break; | break; | ||||
DMESSAGE( "Peakfile: chunksize=%lu, skip=%lu\n", (uint64_t)bh.chunksize, (uint64_t) bh.skip ); | |||||
DMESSAGE( "Peakfile: chunksize=%lu, skip=%lu", (uint64_t)bh.chunksize, (uint64_t) bh.skip ); | |||||
ASSERT( bh.chunksize, "Chucksize of zero. Invalid peak file structure!" ); | ASSERT( bh.chunksize, "Chucksize of zero. Invalid peak file structure!" ); | ||||
@@ -184,11 +184,6 @@ public: | |||||
if ( ! blocks.size() ) | if ( ! blocks.size() ) | ||||
FATAL( "Peak file contains no blocks!" ); | FATAL( "Peak file contains no blocks!" ); | ||||
if ( chunksize == _chunksize ) | |||||
{ | |||||
return; | |||||
/* already on the right block... */ | |||||
} | |||||
// DMESSAGE( "peakfile has %d blocks.", blocks.size() ); | // DMESSAGE( "peakfile has %d blocks.", blocks.size() ); | ||||
@@ -208,7 +203,7 @@ public: | |||||
break; | break; | ||||
} | } | ||||
// DMESSAGE( "using peakfile block for chunksize %lu", _chunksize ); | |||||
// DMESSAGE( "using peakfile block for chunksize %lu", _chunksize ); | |||||
// _blocks = blocks.size(); | // _blocks = blocks.size(); | ||||
_offset = ftello( _fp ); | _offset = ftello( _fp ); | ||||
} | } | ||||
@@ -310,9 +305,6 @@ public: | |||||
/* locate to start position */ | /* locate to start position */ | ||||
/* if ( s > _clip->length() ) */ | |||||
/* return 0; */ | |||||
if ( fseeko( _fp, _offset + ( frame_to_peak( s ) * sizeof( Peak ) ), SEEK_SET ) ) | if ( fseeko( _fp, _offset + ( frame_to_peak( s ) * sizeof( Peak ) ), SEEK_SET ) ) | ||||
{ | { | ||||
DMESSAGE( "failed to seek... peaks not ready?" ); | DMESSAGE( "failed to seek... peaks not ready?" ); | ||||
@@ -359,9 +351,7 @@ public: | |||||
} | } | ||||
if ( feof( _fp) || len < ratio ) | if ( feof( _fp) || len < ratio ) | ||||
{ | |||||
break; | break; | ||||
} | |||||
} | } | ||||
delete[] pbuf; | delete[] pbuf; | ||||
@@ -408,15 +398,14 @@ Peaks::fill_buffer ( float fpp, nframes_t s, nframes_t e ) const | |||||
bool | bool | ||||
Peaks::ready ( nframes_t s, nframes_t npeaks, nframes_t chunksize ) const | Peaks::ready ( nframes_t s, nframes_t npeaks, nframes_t chunksize ) const | ||||
{ | { | ||||
/* if ( _pending ) */ | |||||
/* return false; */ | |||||
if ( ! _peakfile->open( _clip->filename(), _clip->channels(), chunksize ) ) | |||||
return false; | |||||
Peakfile _peakfile; | |||||
int r = _peakfile->ready( s, npeaks ); | |||||
if ( ! _peakfile.open( _clip->filename(), _clip->channels(), chunksize ) ) | |||||
return false; | |||||
_peakfile->close(); | |||||
return _peakfile.ready( s, npeaks ); | |||||
return r; | |||||
} | } | ||||
/** If this returns false, then the peakfile needs to be built */ | /** If this returns false, then the peakfile needs to be built */ | ||||
@@ -694,6 +683,7 @@ Peaks::Streamer::Streamer ( const char *filename, int channels, nframes_t chunks | |||||
fwrite( &bh, sizeof( bh ), 1, _fp ); | fwrite( &bh, sizeof( bh ), 1, _fp ); | ||||
fflush( _fp ); | fflush( _fp ); | ||||
fsync( fileno( _fp ) ); | |||||
} | } | ||||
Peaks::Streamer::~Streamer ( ) | Peaks::Streamer::~Streamer ( ) | ||||
@@ -704,7 +694,7 @@ Peaks::Streamer::~Streamer ( ) | |||||
touch( fileno( _fp ) ); | touch( fileno( _fp ) ); | ||||
// fsync( fileno( _fp ) ); | |||||
fsync( fileno( _fp ) ); | |||||
fclose( _fp ); | fclose( _fp ); | ||||
@@ -723,9 +713,6 @@ Peaks::Streamer::write ( const sample_t *buf, nframes_t nframes ) | |||||
{ | { | ||||
fwrite( _peak, sizeof( Peak ) * _channels, 1, _fp ); | fwrite( _peak, sizeof( Peak ) * _channels, 1, _fp ); | ||||
/* FIXME: shouldn't we just use write() instead? */ | |||||
// fflush( _fp ); | |||||
memset( _peak, 0, sizeof( Peak ) * _channels ); | memset( _peak, 0, sizeof( Peak ) * _channels ); | ||||
_index = 0; | _index = 0; | ||||
@@ -751,6 +738,9 @@ Peaks::Streamer::write ( const sample_t *buf, nframes_t nframes ) | |||||
_index += processed; | _index += processed; | ||||
nframes -= processed; | nframes -= processed; | ||||
} | } | ||||
/* FIXME: shouldn't we just use write() instead? */ | |||||
fflush( _fp ); | |||||
} | } | ||||
@@ -42,6 +42,12 @@ Record_DS::capture_region ( void ) const | |||||
return NULL; | return NULL; | ||||
} | } | ||||
Track::Capture * | |||||
Record_DS::capture ( void ) | |||||
{ | |||||
return _capture; | |||||
} | |||||
/** write /nframes/ from buf to the capture file of the attached track */ | /** write /nframes/ from buf to the capture file of the attached track */ | ||||
void | void | ||||
Record_DS::write_block ( sample_t *buf, nframes_t nframes ) | Record_DS::write_block ( sample_t *buf, nframes_t nframes ) | ||||
@@ -63,6 +63,7 @@ public: | |||||
/* bool seek_pending ( void ); */ | /* bool seek_pending ( void ); */ | ||||
/* void seek ( nframes_t frame ); */ | /* void seek ( nframes_t frame ); */ | ||||
const Audio_Region * capture_region ( void ) const; | const Audio_Region * capture_region ( void ) const; | ||||
Track::Capture * capture ( void ); | |||||
void start ( nframes_t frame ); | void start ( nframes_t frame ); | ||||
void stop ( nframes_t frame ); | void stop ( nframes_t frame ); | ||||
@@ -40,6 +40,15 @@ Track::capture_region ( void ) const | |||||
return NULL; | return NULL; | ||||
} | } | ||||
Track::Capture * | |||||
Track::capture ( void ) | |||||
{ | |||||
if ( record_ds ) | |||||
return record_ds->capture(); | |||||
else | |||||
return NULL; | |||||
} | |||||
void | void | ||||
Track::update_port_names ( void ) | Track::update_port_names ( void ) | ||||
{ | { | ||||
@@ -261,9 +270,9 @@ Track::record ( Capture *c, nframes_t frame ) | |||||
FATAL( "Could not create file for new capture!" ); | FATAL( "Could not create file for new capture!" ); | ||||
/* open it again for reading in the GUI thread */ | /* open it again for reading in the GUI thread */ | ||||
Audio_File *af = Audio_File::from_file( c->audio_file->name() ); | |||||
// Audio_File *af = Audio_File::from_file( c->audio_file->name() ); | |||||
c->region = new Audio_Region( af, sequence(), frame ); | |||||
c->region = new Audio_Region( c->audio_file, sequence(), frame ); | |||||
c->region->prepare(); | c->region->prepare(); | ||||
} | } | ||||
@@ -315,5 +324,5 @@ Track::finalize ( Capture *c, nframes_t frame ) | |||||
c->region->offset( capture_offset ); | c->region->offset( capture_offset ); | ||||
delete c->audio_file; | |||||
// delete c->audio_file; | |||||
} | } |
@@ -193,9 +193,16 @@ public: | |||||
virtual int h ( void ) const { return _sequence->h(); } | virtual int h ( void ) const { return _sequence->h(); } | ||||
/* used by regions */ | /* used by regions */ | ||||
int get_x( nframes_t frame ) const | |||||
{ | |||||
return frame < timeline->xoffset ? _sequence->x() : min( _sequence->x() + _sequence->w(), _sequence->x() + timeline->ts_to_x( frame - timeline->xoffset ) ); | |||||
} | |||||
virtual int x ( void ) const | virtual int x ( void ) const | ||||
{ | { | ||||
return _r->start < timeline->xoffset ? _sequence->x() : min( _sequence->x() + _sequence->w(), _sequence->x() + timeline->ts_to_x( _r->start - timeline->xoffset ) ); | |||||
return get_x( _r->start ); | |||||
} | } | ||||
/* use this as x() when you need to draw lines between widgets */ | /* use this as x() when you need to draw lines between widgets */ | ||||
@@ -70,8 +70,16 @@ public: | |||||
struct Capture | struct Capture | ||||
{ | { | ||||
nframes_t last_frame_drawn; | |||||
Audio_File *audio_file; | Audio_File *audio_file; | ||||
Audio_Region *region; | Audio_Region *region; | ||||
Capture ( ) | |||||
{ | |||||
last_frame_drawn = 0; | |||||
region = 0; | |||||
audio_file = 0; | |||||
} | |||||
}; | }; | ||||
Fl_Color color ( void ) const { return child(0)->color(); } | Fl_Color color ( void ) const { return child(0)->color(); } | ||||
@@ -213,6 +221,7 @@ public: | |||||
/* Engine */ | /* Engine */ | ||||
const Audio_Region *capture_region ( void ) const; | const Audio_Region *capture_region ( void ) const; | ||||
Capture *capture ( void ); | |||||
void resize_buffers ( nframes_t nframes ); | void resize_buffers ( nframes_t nframes ); | ||||
nframes_t process_input ( nframes_t nframes ); | nframes_t process_input ( nframes_t nframes ); | ||||
@@ -99,7 +99,7 @@ Waveform::draw ( int X, int Y, int W, int H, | |||||
fl_color( color ); | fl_color( color ); | ||||
fl_begin_complex_polygon(); | fl_begin_complex_polygon(); | ||||
j = start; | j = start; | ||||
for ( int x = X; x <= X + W; x++, j += skip ) | for ( int x = X; x <= X + W; x++, j += skip ) | ||||
@@ -109,7 +109,7 @@ Waveform::draw ( int X, int Y, int W, int H, | |||||
for ( int x = X + W; x >= X; x--, j -= skip ) | for ( int x = X + W; x >= X; x--, j -= skip ) | ||||
fl_vertex( x, ty - ( halfheight * pbuf[ j ].max ) ); | fl_vertex( x, ty - ( halfheight * pbuf[ j ].max ) ); | ||||
fl_end_complex_polygon(); | fl_end_complex_polygon(); | ||||
} | } | ||||
} | } | ||||