Logo Search packages:      
Sourcecode: ardour version File versions  Download package

source.h

/*
    Copyright (C) 2000 Paul Davis 

    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; if not, write to the Free Software
    Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.

    $Id: source.h,v 1.28 2005/12/28 21:38:54 essej Exp $
*/

#ifndef __ardour_source_h__
#define __ardour_source_h__

#include <list>
#include <vector>
#include <string>

#include <time.h>

#include <sigc++/signal_system.h>

#include <ardour/ardour.h>
#include <ardour/stateful.h>
#include <pbd/xml++.h>

using std::list;
using std::vector;
using std::string;

namespace ARDOUR {

struct PeakData {
    typedef Sample PeakDatum;

    PeakDatum min;
    PeakDatum max;
};

const jack_nframes_t frames_per_peak = 256;

class Source : public Stateful, public SigC::Object 
{
  public:
      Source (bool announce=true);
      Source (const XMLNode&);
      virtual ~Source ();

      const string& name() const { return _name; }
      ARDOUR::id_t  id() const   { return _id; }

      /* returns the number of items in this `source' */

      virtual jack_nframes_t length() const {
            return _length;
      }

      virtual jack_nframes_t read (Sample *dst, jack_nframes_t start, jack_nframes_t cnt) const {
            return 0;
      }

      virtual jack_nframes_t write (Sample *src, jack_nframes_t cnt) {
            return 0;
      }

      uint32_t use_cnt() const { return _use_cnt; }
      void use ();
      void release ();

      virtual void mark_for_remove() = 0;
      virtual void mark_streaming_write_completed () {}

      time_t timestamp() const { return _timestamp; }
      void stamp (time_t when) { _timestamp = when; }

      void set_captured_for (string str) { _captured_for = str; }
      string captured_for() const { return _captured_for; }

      uint32_t read_data_count() const { return _read_data_count; }
      uint32_t write_data_count() const { return _write_data_count; }

      int  read_peaks (PeakData *peaks, jack_nframes_t npeaks, jack_nframes_t start, jack_nframes_t cnt, double samples_per_unit) const;
      int  build_peaks ();
      bool peaks_ready (SigC::Slot0<void>) const;

      static SigC::Signal1<void,Source*> SourceCreated;
             
      SigC::Signal1<void,Source *> GoingAway;
      mutable SigC::Signal0<void>  PeaksReady;
      mutable SigC::Signal2<void,jack_nframes_t,jack_nframes_t>  PeakRangeReady;
      
      XMLNode& get_state ();
      int set_state (const XMLNode&);


      static int  start_peak_thread ();
      static void stop_peak_thread ();

      static void set_build_missing_peakfiles (bool yn) {
            _build_missing_peakfiles = yn;
      }
      static void set_build_peakfiles (bool yn) {
            _build_peakfiles = yn;
      }

  protected:
      static bool _build_missing_peakfiles;
      static bool _build_peakfiles;

      string            _name;
      uint32_t     _use_cnt;
      bool              _peaks_built;
      mutable PBD::Lock _lock;
      jack_nframes_t    _length;
      bool               next_peak_clear_should_notify;
      string             peakpath;
      int                peakfile; /* fd */
      time_t            _timestamp;
      string            _captured_for;

      mutable uint32_t _read_data_count;  // modified in read()
      mutable uint32_t _write_data_count; // modified in write()

      int initialize_peakfile (bool newfile, string path);
      void build_peaks_from_scratch ();

      int  do_build_peak (jack_nframes_t, jack_nframes_t);
      virtual jack_nframes_t read_unlocked (Sample *dst, jack_nframes_t start, jack_nframes_t cnt) const = 0;
      virtual string peak_path(string audio_path) = 0;
      virtual string old_peak_path(string audio_path) = 0;

      static pthread_t peak_thread;
      static bool      have_peak_thread;
      static void*     peak_thread_work(void*);

      static int peak_request_pipe[2];

      struct PeakRequest {
          enum Type {
                Build,
                Quit
          };
      };

      static vector<Source*> pending_peak_sources;
      static PBD::Lock pending_peak_sources_lock;

      static void queue_for_peaks (Source&);
      static void clear_queue_for_peaks ();
      
      struct PeakBuildRecord {
          jack_nframes_t frame;
          jack_nframes_t cnt;

          PeakBuildRecord (jack_nframes_t f, jack_nframes_t c) 
                : frame (f), cnt (c) {}
          PeakBuildRecord (const PeakBuildRecord& other) {
                frame = other.frame;
                cnt = other.cnt;
          }
      };

      list<Source::PeakBuildRecord *> pending_peak_builds;

  private:
      ARDOUR::id_t _id;
      
      bool file_changed (string path);
};

}

#endif /* __ardour_source_h__ */

Generated by  Doxygen 1.6.0   Back to index