/*
Copyright (C) 2013-2016 Carl Hetherington <cth@carlh.net>
- This program is free software; you can redistribute it and/or modify
+ This file is part of DCP-o-matic.
+
+ DCP-o-matic 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,
+ DCP-o-matic 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.
+ along with DCP-o-matic. If not, see <http://www.gnu.org/licenses/>.
*/
#include "timeline_video_content_view.h"
#include "timeline_audio_content_view.h"
#include "timeline_subtitle_content_view.h"
+#include "timeline_atmos_content_view.h"
#include "content_panel.h"
#include "wx_util.h"
#include "lib/film.h"
#include "lib/timer.h"
#include "lib/audio_content.h"
#include "lib/subtitle_content.h"
+#include "lib/video_content.h"
+#include "lib/atmos_mxf_content.h"
#include <wx/graphics.h>
#include <boost/weak_ptr.hpp>
#include <boost/foreach.hpp>
+#include <boost/make_shared.hpp>
#include <list>
#include <iostream>
using std::cout;
using std::max;
using boost::shared_ptr;
+using boost::make_shared;
using boost::weak_ptr;
using boost::dynamic_pointer_cast;
using boost::bind;
SetMinSize (wxSize (640, tracks() * track_height() + 96));
- _tracks_position = Position<int> (_labels_view->bbox().width, 8);
+ _tracks_position = Position<int> (_labels_view->bbox().width, 32);
_film_changed_connection = film->Changed.connect (bind (&Timeline::film_changed, this, _1));
_film_content_changed_connection = film->ContentChanged.connect (bind (&Timeline::film_content_changed, this, _2, _3));
_views.push_back (_reels_view);
_views.push_back (_labels_view);
+ /* XXX: make_shared does not work here on some compilers due to some strange const problem */
+
BOOST_FOREACH (shared_ptr<Content> i, film->content ()) {
- if (dynamic_pointer_cast<VideoContent> (i)) {
- _views.push_back (shared_ptr<TimelineView> (new TimelineVideoContentView (*this, i)));
+ if (i->video) {
+ _views.push_back (shared_ptr<TimelineContentView> (new TimelineVideoContentView (*this, i)));
+ }
+
+ if (i->audio && !i->audio->mapping().mapped_output_channels().empty ()) {
+ _views.push_back (shared_ptr<TimelineContentView> (new TimelineAudioContentView (*this, i)));
}
- shared_ptr<AudioContent> ac = dynamic_pointer_cast<AudioContent> (i);
- if (ac && !ac->audio_mapping().mapped_output_channels().empty ()) {
- _views.push_back (shared_ptr<TimelineView> (new TimelineAudioContentView (*this, i)));
+ if (i->subtitle) {
+ _views.push_back (shared_ptr<TimelineContentView> (new TimelineSubtitleContentView (*this, i)));
}
- shared_ptr<SubtitleContent> sc = dynamic_pointer_cast<SubtitleContent> (i);
- if (sc && sc->has_subtitles ()) {
- _views.push_back (shared_ptr<TimelineView> (new TimelineSubtitleContentView (*this, sc)));
+ if (dynamic_pointer_cast<AtmosMXFContent> (i)) {
+ _views.push_back (shared_ptr<TimelineContentView> (new TimelineAtmosContentView (*this, i)));
}
}
{
ensure_ui_thread ();
- if (property == AudioContentProperty::AUDIO_STREAMS) {
+ if (property == AudioContentProperty::STREAMS) {
recreate_views ();
} else if (!frequent) {
setup_pixels_per_second ();
}
}
+ /* See if we have any subtitle / atmos / right-eye views */
+ bool have_3d = false;
+ bool have_subtitle = false;
+ bool have_atmos = false;
+ BOOST_FOREACH (shared_ptr<TimelineView> i, _views) {
+ shared_ptr<TimelineContentView> cv = dynamic_pointer_cast<TimelineContentView> (i);
+ if (!cv) {
+ continue;
+ }
+
+ if (dynamic_pointer_cast<TimelineVideoContentView> (i)) {
+ if (cv->content()->video->frame_type() == VIDEO_FRAME_TYPE_3D_RIGHT) {
+ have_3d = true;
+ }
+ } else if (dynamic_pointer_cast<TimelineSubtitleContentView> (i)) {
+ have_subtitle = true;
+ } else if (dynamic_pointer_cast<TimelineAtmosContentView> (i)) {
+ have_atmos = true;
+ }
+ }
+
+ _labels_view->set_3d (have_3d);
+ _labels_view->set_subtitle (have_subtitle);
+ _labels_view->set_atmos (have_atmos);
+
+ /* Hence decide where to start subtitle, atmos and audio tracks */
+ int const subtitle = have_3d ? 2 : 1;
+ int const atmos = have_subtitle ? subtitle + 1 : subtitle;
+ int const audio = have_atmos ? atmos + 1: atmos;
+
for (TimelineViewList::iterator i = _views.begin(); i != _views.end(); ++i) {
shared_ptr<TimelineContentView> cv = dynamic_pointer_cast<TimelineContentView> (*i);
if (!cv) {
}
if (dynamic_pointer_cast<TimelineVideoContentView> (*i)) {
- /* Video on track 0 */
- cv->set_track (0);
- _tracks = max (_tracks, 1);
+ /* Video on tracks 0 and maybe 1 (left and right eye) */
+ cv->set_track (cv->content()->video->frame_type() == VIDEO_FRAME_TYPE_3D_RIGHT ? 1 : 0);
+ _tracks = max (_tracks, have_3d ? 2 : 1);
continue;
} else if (dynamic_pointer_cast<TimelineSubtitleContentView> (*i)) {
- /* Subtitles on track 1 */
- cv->set_track (1);
- _tracks = max (_tracks, 2);
+ cv->set_track (subtitle);
+ _tracks = max (_tracks, subtitle + 1);
+ continue;
+ } else if (dynamic_pointer_cast<TimelineAtmosContentView> (*i)) {
+ cv->set_track (atmos);
+ _tracks = max (_tracks, atmos + 1);
continue;
}
- /* Audio on tracks 2 and up */
- int t = 2;
+ int t = audio;
shared_ptr<Content> content = cv->content();
DCPTimePeriod content_period (content->position(), content->end());
}
_time_axis_view->set_y (tracks() * track_height() + 64);
- _reels_view->set_y (tracks() * track_height() + 32);
+ _reels_view->set_y (8);
}
int