/*
- Copyright (C) 2015 Carl Hetherington <cth@carlh.net>
+ Copyright (C) 2015-2016 Carl Hetherington <cth@carlh.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
#include "audio_mapping.h"
#include "util.h"
-AudioStream::AudioStream (int frame_rate, int channels)
+AudioStream::AudioStream (int frame_rate, Frame length, int channels)
: _frame_rate (frame_rate)
+ , _length (length)
{
_mapping = AudioMapping (channels, MAX_DCP_AUDIO_CHANNELS);
}
-AudioStream::AudioStream (int frame_rate, AudioMapping mapping)
+AudioStream::AudioStream (int frame_rate, Frame length, AudioMapping mapping)
: _frame_rate (frame_rate)
+ , _length (length)
, _mapping (mapping)
{
/*
- Copyright (C) 2015 Carl Hetherington <cth@carlh.net>
+ Copyright (C) 2015-2016 Carl Hetherington <cth@carlh.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
#define DCPOMATIC_AUDIO_STREAM_H
#include "audio_mapping.h"
+#include "types.h"
#include <boost/thread/mutex.hpp>
struct audio_sampling_rate_test;
class AudioStream
{
public:
- AudioStream (int frame_rate, int channels);
- AudioStream (int frame_rate, AudioMapping mapping);
+ AudioStream (int frame_rate, Frame length, int channels);
+ AudioStream (int frame_rate, Frame length, AudioMapping mapping);
virtual ~AudioStream () {}
void set_mapping (AudioMapping mapping);
return _frame_rate;
}
+ Frame length () const {
+ boost::mutex::scoped_lock lm (_mutex);
+ return _length;
+ }
+
int channels () const;
protected:
friend struct player_time_calculation_test3;
int _frame_rate;
+ Frame _length;
AudioMapping _mapping;
};
audio->set_stream (
AudioStreamPtr (
- new AudioStream (node->number_child<int> ("AudioFrameRate"), AudioMapping (node->node_child ("AudioMapping"), version))
+ new AudioStream (
+ node->number_child<int> ("AudioFrameRate"),
+ node->number_child<Frame> ("AudioLength"),
+ AudioMapping (node->node_child ("AudioMapping"), version)
+ )
)
);
{
boost::mutex::scoped_lock lm (_mutex);
- AudioStreamPtr as (new AudioStream (examiner->audio_frame_rate(), examiner->audio_channels ()));
+ AudioStreamPtr as (new AudioStream (examiner->audio_frame_rate(), examiner->audio_length(), examiner->audio_channels()));
audio->set_stream (as);
AudioMapping m = as->mapping ();
film()->make_audio_mapping_default (m);
if (audio) {
audio->as_xml (node);
node->add_child("AudioFrameRate")->add_child_text (raw_convert<string> (audio->stream()->frame_rate()));
+ node->add_child("AudioLength")->add_child_text (raw_convert<string> (audio->stream()->length()));
audio->stream()->mapping().as_xml (node->add_child("AudioMapping"));
}
FFmpegAudioStream::FFmpegAudioStream (cxml::ConstNodePtr node, int version)
: FFmpegStream (node)
- , AudioStream (node->number_child<int> ("FrameRate"), AudioMapping (node->node_child ("Mapping"), version))
+ , AudioStream (
+ node->number_child<int> ("FrameRate"),
+ node->optional_number_child<Frame>("Length").get_value_or (0),
+ AudioMapping (node->node_child ("Mapping"), version)
+ )
{
optional<ContentTime::Type> const f = node->optional_number_child<ContentTime::Type> ("FirstAudio");
if (f) {
{
FFmpegStream::as_xml (root);
root->add_child("FrameRate")->add_child_text (raw_convert<string> (frame_rate ()));
+ root->add_child("Length")->add_child_text (raw_convert<string> (length ()));
mapping().as_xml (root->add_child("Mapping"));
if (first_audio) {
root->add_child("FirstAudio")->add_child_text (raw_convert<string> (first_audio.get().get ()));
class FFmpegAudioStream : public FFmpegStream, public AudioStream
{
public:
- FFmpegAudioStream (std::string name, int id, int frame_rate, int channels)
+ FFmpegAudioStream (std::string name, int id, int frame_rate, Frame length, int channels)
: FFmpegStream (name, id)
- , AudioStream (frame_rate, channels)
+ , AudioStream (frame_rate, length, channels)
{}
FFmpegAudioStream (cxml::ConstNodePtr, int);
/* Constructor for tests */
FFmpegAudioStream ()
: FFmpegStream ("", 0)
- , AudioStream (0, 0)
+ , AudioStream (0, 0, 0)
{}
};
s->codec->channel_layout = av_get_default_channel_layout (s->codec->channels);
}
+ DCPOMATIC_ASSERT (_format_context->duration != AV_NOPTS_VALUE);
+
_audio_streams.push_back (
shared_ptr<FFmpegAudioStream> (
- new FFmpegAudioStream (audio_stream_name (s), s->id, s->codec->sample_rate, s->codec->channels)
+ new FFmpegAudioStream (
+ audio_stream_name (s),
+ s->id,
+ s->codec->sample_rate,
+ (double (_format_context->duration) / AV_TIME_BASE) * s->codec->sample_rate,
+ s->codec->channels
+ )
)
);
SndfileContent::SndfileContent (shared_ptr<const Film> film, cxml::ConstNodePtr node, int version)
: Content (film, node)
- , _audio_length (node->number_child<Frame> ("AudioLength"))
{
audio = AudioContent::from_xml (this, film, node);
if (audio) {
audio->set_stream (
AudioStreamPtr (
- new AudioStream (node->number_child<int> ("AudioFrameRate"), AudioMapping (node->node_child ("AudioMapping"), version)))
+ new AudioStream (
+ node->number_child<int> ("AudioFrameRate"),
+ node->number_child<Frame> ("AudioLength"),
+ AudioMapping (node->node_child ("AudioMapping"), version)
+ )
+ )
);
}
}
if (audio) {
audio->as_xml (node);
node->add_child("AudioFrameRate")->add_child_text (raw_convert<string> (audio->stream()->frame_rate ()));
+ node->add_child("AudioLength")->add_child_text (raw_convert<string> (audio->stream()->length ()));
audio->stream()->mapping().as_xml (node->add_child("AudioMapping"));
}
-
- node->add_child("AudioLength")->add_child_text (raw_convert<string> (audio_length ()));
}
{
boost::mutex::scoped_lock lm (_mutex);
- AudioStreamPtr as (new AudioStream (ex->audio_frame_rate(), ex->audio_channels ()));
+ AudioStreamPtr as (new AudioStream (ex->audio_frame_rate(), ex->audio_length(), ex->audio_channels ()));
audio->set_stream (as);
AudioMapping m = as->mapping ();
film()->make_audio_mapping_default (m);
as->set_mapping (m);
- _audio_length = ex->audio_length ();
}
signal_changed (AudioContentProperty::STREAMS);
SndfileContent::full_length () const
{
FrameRateChange const frc (active_video_frame_rate(), film()->video_frame_rate());
- return DCPTime::from_frames (audio_length() / frc.speed_up, audio->stream()->frame_rate ());
+ return DCPTime::from_frames (audio->stream()->length() / frc.speed_up, audio->stream()->frame_rate ());
}
void as_xml (xmlpp::Node *) const;
static bool valid_file (boost::filesystem::path);
-
-private:
- Frame audio_length () const {
- boost::mutex::scoped_lock lm (_mutex);
- return _audio_length;
- }
-
- Frame _audio_length;
};
#endif
: Content (film)
{
audio.reset (new AudioContent (this, film));
- audio->set_stream (AudioStreamPtr (new AudioStream (48000, 2)));
+ audio->set_stream (AudioStreamPtr (new AudioStream (48000, audio_length(), 2)));
}
std::string summary () const {
afr.push_back (30);
Config::instance()->set_allowed_dcp_frame_rates (afr);
- shared_ptr<FFmpegAudioStream> stream (new FFmpegAudioStream ("foo", 0, 0, 0));
+ shared_ptr<FFmpegAudioStream> stream (new FFmpegAudioStream ("foo", 0, 0, 0, 0));
content->audio->add_stream (stream);
content->_video_frame_rate = 24;
film->set_video_frame_rate (24);