+ std::string file (std::string f) const;
+ std::string dir (std::string d) const;
+
+ std::string content_path () const;
+ ContentType content_type () const;
+
+ int target_audio_sample_rate () const;
+
+ void write_metadata () const;
+ void read_metadata ();
+
+ libdcp::Size cropped_size (libdcp::Size) const;
+ std::string dci_name () const;
+ std::string dcp_name () const;
+
+ boost::optional<int> dcp_intrinsic_duration () const {
+ return _dcp_intrinsic_duration;
+ }
+
+ /** @return true if our state has changed since we last saved it */
+ bool dirty () const {
+ return _dirty;
+ }
+
+ int audio_channels () const;
+
+ void set_dci_date_today ();
+
+ /** Identifiers for the parts of our state;
+ used for signalling changes.
+ */
+ enum Property {
+ NONE,
+ NAME,
+ USE_DCI_NAME,
+ CONTENT,
+ TRUST_CONTENT_HEADER,
+ DCP_CONTENT_TYPE,
+ FORMAT,
+ CROP,
+ FILTERS,
+ SCALER,
+ TRIM_START,
+ TRIM_END,
+ DCP_AB,
+ CONTENT_AUDIO_STREAM,
+ EXTERNAL_AUDIO,
+ USE_CONTENT_AUDIO,
+ AUDIO_GAIN,
+ AUDIO_DELAY,
+ STILL_DURATION,
+ SUBTITLE_STREAM,
+ WITH_SUBTITLES,
+ SUBTITLE_OFFSET,
+ SUBTITLE_SCALE,
+ COLOUR_LUT,
+ J2K_BANDWIDTH,
+ DCI_METADATA,
+ SIZE,
+ LENGTH,
+ DCP_INTRINSIC_DURATION,
+ CONTENT_AUDIO_STREAMS,
+ SUBTITLE_STREAMS,
+ FRAMES_PER_SECOND,
+ };
+
+
+ /* GET */
+
+ std::string directory () const {
+ boost::mutex::scoped_lock lm (_directory_mutex);
+ return _directory;
+ }
+
+ std::string name () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _name;
+ }
+
+ bool use_dci_name () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _use_dci_name;
+ }
+
+ std::string content () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _content;
+ }
+
+ bool trust_content_header () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _trust_content_header;
+ }
+
+ DCPContentType const * dcp_content_type () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _dcp_content_type;
+ }
+
+ Format const * format () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _format;
+ }
+
+ Crop crop () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _crop;
+ }
+
+ std::vector<Filter const *> filters () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _filters;
+ }
+
+ Scaler const * scaler () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _scaler;
+ }
+
+ int trim_start () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _trim_start;
+ }
+
+ int trim_end () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _trim_end;
+ }
+
+ bool dcp_ab () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _dcp_ab;
+ }
+
+ boost::shared_ptr<AudioStream> content_audio_stream () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _content_audio_stream;
+ }
+
+ std::vector<std::string> external_audio () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _external_audio;
+ }
+
+ bool use_content_audio () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _use_content_audio;
+ }
+
+ float audio_gain () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _audio_gain;
+ }
+
+ int audio_delay () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _audio_delay;
+ }
+
+ int still_duration () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _still_duration;
+ }
+
+ int still_duration_in_frames () const;
+
+ boost::shared_ptr<SubtitleStream> subtitle_stream () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _subtitle_stream;
+ }
+
+ bool with_subtitles () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _with_subtitles;
+ }
+
+ int subtitle_offset () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _subtitle_offset;
+ }
+
+ float subtitle_scale () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _subtitle_scale;
+ }
+
+ int colour_lut () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _colour_lut;
+ }
+
+ int j2k_bandwidth () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _j2k_bandwidth;
+ }
+
+ std::string audio_language () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _audio_language;
+ }
+
+ std::string subtitle_language () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _subtitle_language;
+ }
+
+ std::string territory () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _territory;
+ }
+
+ std::string rating () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _rating;
+ }
+
+ std::string studio () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _studio;
+ }
+
+ std::string facility () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _facility;
+ }
+
+ std::string package_type () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _package_type;
+ }
+
+ libdcp::Size size () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _size;
+ }
+
+ boost::optional<SourceFrame> length () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _length;
+ }
+
+ std::string content_digest () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _content_digest;
+ }
+
+ std::vector<boost::shared_ptr<AudioStream> > content_audio_streams () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _content_audio_streams;
+ }
+
+ std::vector<boost::shared_ptr<SubtitleStream> > subtitle_streams () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ return _subtitle_streams;
+ }
+
+ float frames_per_second () const {
+ boost::mutex::scoped_lock lm (_state_mutex);
+ if (content_type() == STILL) {
+ return 24;
+ }
+
+ return _frames_per_second;
+ }
+
+ boost::shared_ptr<AudioStream> audio_stream () const;
+
+
+ /* SET */
+
+ void set_directory (std::string);
+ void set_name (std::string);
+ void set_use_dci_name (bool);
+ void set_content (std::string);
+ void set_trust_content_header (bool);
+ void set_dcp_content_type (DCPContentType const *);
+ void set_format (Format const *);
+ void set_crop (Crop);
+ void set_left_crop (int);
+ void set_right_crop (int);
+ void set_top_crop (int);
+ void set_bottom_crop (int);
+ void set_filters (std::vector<Filter const *>);
+ void set_scaler (Scaler const *);
+ void set_trim_start (int);
+ void set_trim_end (int);
+ void set_dcp_ab (bool);
+ void set_content_audio_stream (boost::shared_ptr<AudioStream>);
+ void set_external_audio (std::vector<std::string>);
+ void set_use_content_audio (bool);
+ void set_audio_gain (float);
+ void set_audio_delay (int);
+ void set_still_duration (int);
+ void set_subtitle_stream (boost::shared_ptr<SubtitleStream>);
+ void set_with_subtitles (bool);
+ void set_subtitle_offset (int);
+ void set_subtitle_scale (float);
+ void set_colour_lut (int);
+ void set_j2k_bandwidth (int);
+ void set_audio_language (std::string);
+ void set_subtitle_language (std::string);
+ void set_territory (std::string);
+ void set_rating (std::string);
+ void set_studio (std::string);
+ void set_facility (std::string);
+ void set_package_type (std::string);
+ void set_size (libdcp::Size);
+ void set_length (SourceFrame);
+ void unset_length ();
+ void set_dcp_intrinsic_duration (int);
+ void set_content_digest (std::string);
+ void set_content_audio_streams (std::vector<boost::shared_ptr<AudioStream> >);
+ void set_subtitle_streams (std::vector<boost::shared_ptr<SubtitleStream> >);
+ void set_frames_per_second (float);
+
+ /** Emitted when some property has changed */
+ mutable boost::signals2::signal<void (Property)> Changed;
+
+ /** Current version number of the state file */
+ static int const state_version;
+