Files
oak-editor/app/widget/videoparamedit/videoparamedit.cpp
T
itsmattkc abf1eff866 add ability to enter custom frame rates
We ain't gatekeeping frame rates
2021-05-03 17:49:47 +10:00

392 lines
13 KiB
C++

/***
Olive - Non-Linear Video Editor
Copyright (C) 2021 Olive Team
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 3 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, see <http://www.gnu.org/licenses/>.
***/
#include "videoparamedit.h"
#include <QGridLayout>
namespace olive {
VideoParamEdit::VideoParamEdit(QWidget* parent) :
QWidget(parent),
color_manager_(nullptr),
mask_(0)
{
QGridLayout* layout = new QGridLayout(this);
layout->setMargin(0);
int row = 0;
// Enabled
enabled_lbl_ = new QLabel(tr("Enabled:"));
layout->addWidget(enabled_lbl_, row, 0);
enabled_box_ = new QCheckBox();
connect(enabled_box_, &QCheckBox::clicked, this, &VideoParamEdit::Changed);
layout->addWidget(enabled_box_, row, 1);
row++;
// Width
width_lbl_ = new QLabel(tr("Width:"));
layout->addWidget(width_lbl_, row, 0);
width_slider_ = new IntegerSlider();
width_slider_->SetMinimum(1);
width_slider_->SetMaximum(32768);
connect(width_slider_, &IntegerSlider::ValueChanged, this, &VideoParamEdit::Changed);
layout->addWidget(width_slider_, row, 1);
row++;
// Height
height_lbl_ = new QLabel(tr("Height:"));
layout->addWidget(height_lbl_, row, 0);
height_slider_ = new IntegerSlider();
height_slider_->SetMinimum(1);
height_slider_->SetMaximum(32768);
connect(height_slider_, &IntegerSlider::ValueChanged, this, &VideoParamEdit::Changed);
layout->addWidget(height_slider_, row, 1);
row++;
// Depth
depth_lbl_ = new QLabel(tr("Depth:"));
layout->addWidget(depth_lbl_, row, 0);
depth_slider_ = new IntegerSlider();
depth_slider_->SetMinimum(1);
depth_slider_->SetMaximum(32768);
connect(depth_slider_, &IntegerSlider::ValueChanged, this, &VideoParamEdit::Changed);
layout->addWidget(depth_slider_, row, 1);
row++;
// Pixel Format
format_lbl_ = new QLabel(tr("Format:"));
layout->addWidget(format_lbl_, row, 0);
format_combobox_ = new PixelFormatComboBox(true);
connect(format_combobox_, static_cast<void (PixelFormatComboBox::*)(int)>(&PixelFormatComboBox::currentIndexChanged), this, &VideoParamEdit::Changed);
layout->addWidget(format_combobox_, row, 1);
row++;
// Frame Rate
frame_rate_lbl_ = new QLabel(tr("Frame Rate:"));
layout->addWidget(frame_rate_lbl_, row, 0);
frame_rate_combobox_ = new FrameRateComboBox();
connect(frame_rate_combobox_, &FrameRateComboBox::FrameRateChanged, this, &VideoParamEdit::Changed);
layout->addWidget(frame_rate_combobox_, row, 1);
frame_rate_slider_ = new RationalSlider();
frame_rate_slider_->SetMinimum(0);
frame_rate_slider_->SetDecimalPlaces(3);
frame_rate_slider_->SetAutoTrimDecimalPlaces(true);
frame_rate_slider_->SetTimebase(rational(1, 1000)); // Drag interval
frame_rate_slider_->DisableDisplayType(RationalSlider::kTime);
connect(frame_rate_slider_, &RationalSlider::ValueChanged, this, &VideoParamEdit::Changed);
layout->addWidget(frame_rate_slider_, row, 1);
row++;
// Pixel Aspect Ratio
pixel_aspect_lbl_ = new QLabel(tr("Pixel Aspect Ratio:"));
layout->addWidget(pixel_aspect_lbl_, row, 0);
pixel_aspect_combobox_ = new PixelAspectRatioComboBox();
connect(pixel_aspect_combobox_, static_cast<void (PixelAspectRatioComboBox::*)(int)>(&PixelAspectRatioComboBox::currentIndexChanged), this, &VideoParamEdit::Changed);
layout->addWidget(pixel_aspect_combobox_, row, 1);
row++;
// Interlacing
interlaced_lbl_ = new QLabel(tr("Interlacing:"));
layout->addWidget(interlaced_lbl_, row, 0);
interlaced_combobox_ = new InterlacedComboBox();
connect(interlaced_combobox_, static_cast<void (InterlacedComboBox::*)(int)>(&InterlacedComboBox::currentIndexChanged), this, &VideoParamEdit::Changed);
layout->addWidget(interlaced_combobox_, row, 1);
row++;
// Channel Count
channel_count_lbl_ = new QLabel(tr("Channel Count:"));
layout->addWidget(channel_count_lbl_, row, 0);
channel_count_combobox_ = new QComboBox();
channel_count_combobox_->addItem(tr("RGB"), VideoParams::kRGBChannelCount);
channel_count_combobox_->addItem(tr("RGBA"), VideoParams::kRGBAChannelCount);
connect(channel_count_combobox_, static_cast<void (QComboBox::*)(int)>(&QComboBox::currentIndexChanged), this, &VideoParamEdit::Changed);
layout->addWidget(channel_count_combobox_, row, 1);
row++;
// Divider
divider_lbl_ = new QLabel(tr("Divider:"));
layout->addWidget(divider_lbl_, row, 0);
divider_combobox_ = new VideoDividerComboBox();
connect(divider_combobox_, static_cast<void (VideoDividerComboBox::*)(int)>(&VideoDividerComboBox::currentIndexChanged), this, &VideoParamEdit::Changed);
layout->addWidget(divider_combobox_, row, 1);
row++;
// Stream Index
stream_index_lbl_ = new QLabel(tr("Stream Index:"));
layout->addWidget(stream_index_lbl_, row, 0);
stream_index_slider_ = new IntegerSlider();
stream_index_slider_->SetMinimum(0);
connect(stream_index_slider_, &IntegerSlider::ValueChanged, this, &VideoParamEdit::Changed);
layout->addWidget(stream_index_slider_, row, 1);
row++;
// Video type
video_type_lbl_ = new QLabel(tr("Video Type:"));
layout->addWidget(video_type_lbl_, row, 0);
video_type_combobox_ = new QComboBox();
video_type_combobox_->addItem(tr("Video"), VideoParams::kVideoTypeVideo);
video_type_combobox_->addItem(tr("Still"), VideoParams::kVideoTypeStill);
video_type_combobox_->addItem(tr("Image Sequence"), VideoParams::kVideoTypeImageSequence);
connect(video_type_combobox_, static_cast<void (QComboBox::*)(int)>(&QComboBox::currentIndexChanged), this, &VideoParamEdit::Changed);
layout->addWidget(video_type_combobox_, row, 1);
row++;
// Start time (for image sequences)
start_time_lbl_ = new QLabel(tr("Start Time"));
layout->addWidget(start_time_lbl_, row, 0);
start_time_slider_ = new IntegerSlider();
start_time_slider_->SetMinimum(0);
connect(start_time_slider_, &IntegerSlider::ValueChanged, this, &VideoParamEdit::Changed);
layout->addWidget(start_time_slider_, row, 1);
row++;
// End time (for image sequences)
end_time_lbl_ = new QLabel(tr("End Time"));
layout->addWidget(end_time_lbl_, row, 0);
end_time_slider_ = new IntegerSlider();
end_time_slider_->SetMinimum(0);
connect(end_time_slider_, &IntegerSlider::ValueChanged, this, &VideoParamEdit::Changed);
layout->addWidget(end_time_slider_, row, 1);
row++;
// Premultiplied alpha
premultiplied_alpha_lbl_ = new QLabel(tr("Premultiplied Alpha"));
layout->addWidget(premultiplied_alpha_lbl_, row, 0);
premultiplied_alpha_box_ = new QCheckBox();
connect(premultiplied_alpha_box_, &QCheckBox::clicked, this, &VideoParamEdit::Changed);
layout->addWidget(premultiplied_alpha_box_, row, 1);
row++;
// Colorspace
colorspace_lbl_ = new QLabel(tr("Colorspace"));
layout->addWidget(colorspace_lbl_, row, 0);
colorspace_combobox_ = new QComboBox();
connect(colorspace_combobox_, static_cast<void (QComboBox::*)(int)>(&QComboBox::currentIndexChanged), this, &VideoParamEdit::Changed);
layout->addWidget(colorspace_combobox_, row, 1);
}
void VideoParamEdit::SetParameterMask(uint64_t mask)
{
mask_ = mask;
width_lbl_->setVisible(mask & kWidthHeight);
width_slider_->setVisible(mask & kWidthHeight);
height_lbl_->setVisible(mask & kWidthHeight);
height_slider_->setVisible(mask & kWidthHeight);
depth_lbl_->setVisible(mask & kDepth);
depth_slider_->setVisible(mask & kDepth);
frame_rate_lbl_->setVisible(mask & kFrameRate);
frame_rate_combobox_->setVisible((mask & kFrameRate) && !(mask & kFrameRateIsArbitrary));
frame_rate_slider_->setVisible((mask & kFrameRate) && (mask & kFrameRateIsArbitrary));
pixel_aspect_lbl_->setVisible(mask & kPixelAspect);
pixel_aspect_combobox_->setVisible(mask & kPixelAspect);
interlaced_lbl_->setVisible(mask & kInterlacing);
interlaced_combobox_->setVisible(mask & kInterlacing);
enabled_lbl_->setVisible(mask & kEnabled);
enabled_box_->setVisible(mask & kEnabled);
format_lbl_->setVisible(mask & kFormat);
format_combobox_->setVisible(mask & kFormat);
channel_count_lbl_->setVisible(mask & kChannelCount);
channel_count_combobox_->setVisible(mask & kChannelCount);
divider_lbl_->setVisible(mask & kDivider);
divider_combobox_->setVisible(mask & kDivider);
stream_index_lbl_->setVisible(mask & kStreamIndex);
stream_index_slider_->setVisible(mask & kStreamIndex);
video_type_lbl_->setVisible(mask & kIsImageSequence);
video_type_combobox_->setVisible(mask & kIsImageSequence);
start_time_lbl_->setVisible(mask & kStartTime);
start_time_slider_->setVisible(mask & kStartTime);
end_time_lbl_->setVisible(mask & kEndTime);
end_time_slider_->setVisible(mask & kEndTime);
premultiplied_alpha_lbl_->setVisible(mask & kPremultipliedAlpha);
premultiplied_alpha_box_->setVisible(mask & kPremultipliedAlpha);
colorspace_lbl_->setVisible(mask & kColorspace);
colorspace_combobox_->setVisible(mask & kColorspace);
}
VideoParams VideoParamEdit::GetVideoParams() const
{
VideoParams p;
p.set_enabled(enabled_box_->isChecked());
p.set_width(width_slider_->GetValue());
p.set_height(height_slider_->GetValue());
p.set_depth(depth_slider_->GetValue());
{
rational using_frame_rate;
if (mask_ & kFrameRateIsArbitrary) {
using_frame_rate = frame_rate_slider_->GetValue();
} else {
using_frame_rate = frame_rate_combobox_->GetFrameRate();
}
p.set_frame_rate(using_frame_rate);
if (mask_ & kFrameRateIsNotTimebase) {
// Frame rate editor will only edit the frame rate
p.set_time_base(timebase_temp_);
} else {
p.set_time_base(using_frame_rate.flipped());
}
}
p.set_pixel_aspect_ratio(pixel_aspect_combobox_->GetPixelAspectRatio());
p.set_interlacing(interlaced_combobox_->GetInterlaceMode());
p.set_format(format_combobox_->GetPixelFormat());
p.set_channel_count(channel_count_combobox_->currentData().toInt());
p.set_divider(divider_combobox_->GetDivider());
p.set_stream_index(stream_index_slider_->GetValue());
p.set_video_type(static_cast<VideoParams::Type>(video_type_combobox_->currentData().toInt()));
p.set_start_time(start_time_slider_->GetValue());
p.set_duration(end_time_slider_->GetValue() - start_time_slider_->GetValue() + 1);
p.set_premultiplied_alpha(premultiplied_alpha_box_->isChecked());
p.set_colorspace(colorspace_combobox_->currentData().toString());
return p;
}
void VideoParamEdit::SetVideoParams(const VideoParams &p)
{
blockSignals(true);
enabled_box_->setChecked(p.enabled());
width_slider_->SetValue(p.width());
height_slider_->SetValue(p.height());
depth_slider_->SetValue(p.depth());
frame_rate_combobox_->SetFrameRate(p.frame_rate());
frame_rate_slider_->SetValue(p.frame_rate());
timebase_temp_ = p.time_base();
pixel_aspect_combobox_->SetPixelAspectRatio(p.pixel_aspect_ratio());
interlaced_combobox_->SetInterlaceMode(p.interlacing());
format_combobox_->SetPixelFormat(p.format());
SetChannelCount(p.channel_count());
divider_combobox_->SetDivider(p.divider());
stream_index_slider_->SetValue(p.stream_index());
SetVideoTypeComboBox(p.video_type());
start_time_slider_->SetValue(p.start_time());
end_time_slider_->SetValue(p.start_time() + p.duration() - 1);
premultiplied_alpha_box_->setChecked(p.premultiplied_alpha());
if (color_manager_) {
// Assume colorspace box has been populated correctly
for (int i=0; i<colorspace_combobox_->count(); i++) {
if (colorspace_combobox_->itemData(i).toString() == p.colorspace()) {
colorspace_combobox_->setCurrentIndex(i);
break;
}
}
} else {
// Box is empty, fill with single option so that it gets preserved in GetVideoParams()
colorspace_combobox_->clear();
colorspace_combobox_->addItem(p.colorspace(), p.colorspace());
}
blockSignals(false);
}
void VideoParamEdit::SetColorManager(ColorManager *cm)
{
color_manager_ = cm;
// Re-populate colorspace combobox
colorspace_combobox_->clear();
if (color_manager_) {
// Add default colorspace
colorspace_combobox_->addItem(tr("Default (%1)").arg(color_manager_->GetDefaultInputColorSpace()), QString());
// Add remaining
QStringList spaces = color_manager_->ListAvailableColorspaces();
foreach (const QString& s, spaces) {
colorspace_combobox_->addItem(s, s);
}
}
}
void VideoParamEdit::SetChannelCount(int count)
{
for (int i=0; i<channel_count_combobox_->count(); i++) {
if (channel_count_combobox_->itemData(i).toInt() == count) {
channel_count_combobox_->setCurrentIndex(i);
break;
}
}
}
void VideoParamEdit::SetVideoTypeComboBox(VideoParams::Type type)
{
for (int i=0; i<video_type_combobox_->count(); i++) {
if (video_type_combobox_->itemData(i).toInt() == type) {
video_type_combobox_->setCurrentIndex(i);
break;
}
}
}
}