successfully transmit block map
Requires a binary data type, which requires a new project serializer
This commit is contained in:
@@ -46,7 +46,8 @@ Track::Track() :
|
||||
index_(-1),
|
||||
locked_(false),
|
||||
sequence_(nullptr),
|
||||
ignore_arraymap_(0)
|
||||
ignore_arraymap_(0),
|
||||
arraymap_invalid_(false)
|
||||
{
|
||||
AddInput(kBlockInput, NodeValue::kNone, InputFlags(kInputFlagArray | kInputFlagNotKeyframable | kInputFlagHidden));
|
||||
|
||||
@@ -205,33 +206,11 @@ void Track::InputValueChangedEvent(const QString &input, int element)
|
||||
|
||||
if (input == kMutedInput) {
|
||||
emit MutedChanged(IsMuted());
|
||||
} else if (false && input == kArrayMapInput) {
|
||||
} else if (input == kArrayMapInput) {
|
||||
if (ignore_arraymap_ > 0) {
|
||||
qDebug() << "ignored our own array map update";
|
||||
ignore_arraymap_--;
|
||||
} else {
|
||||
qDebug() << "received REAL array map update";
|
||||
|
||||
block_array_indexes_ = GetStandardValue(kArrayMapInput).value< QVector<int> >();
|
||||
blocks_.reserve(block_array_indexes_.size());
|
||||
Block *prev = nullptr;
|
||||
for (int i = 0; i < block_array_indexes_.size(); i++) {
|
||||
Block *b = static_cast<Block*>(GetConnectedOutput(kBlockInput, block_array_indexes_.at(i)));
|
||||
|
||||
Block::set_previous_next(prev, b);
|
||||
|
||||
if (b) {
|
||||
blocks_.append(b);
|
||||
prev = b;
|
||||
} else {
|
||||
block_array_indexes_.removeAt(i);
|
||||
i--;
|
||||
}
|
||||
}
|
||||
if (prev) {
|
||||
prev->set_next(nullptr);
|
||||
}
|
||||
UpdateInOutFrom(0);
|
||||
RefreshBlockCacheFromArrayMap();
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -427,8 +406,7 @@ void Track::InsertBlockAtIndex(Block *block, int index)
|
||||
|
||||
emit BlockAdded(block);
|
||||
|
||||
ignore_arraymap_++;
|
||||
SetStandardValue(kArrayMapInput, QVariant::fromValue(block_array_indexes_));
|
||||
UpdateArrayMap();
|
||||
}
|
||||
|
||||
void Track::AppendBlock(Block *block)
|
||||
@@ -472,8 +450,7 @@ void Track::RippleRemoveBlock(Block *block)
|
||||
|
||||
Node::InvalidateCache(TimeRange(remove_in, qMax(track_length(), remove_out)), kBlockInput);
|
||||
|
||||
ignore_arraymap_++;
|
||||
SetStandardValue(kArrayMapInput, QVariant::fromValue(block_array_indexes_));
|
||||
UpdateArrayMap();
|
||||
}
|
||||
|
||||
void Track::ReplaceBlock(Block *old, Block *replace)
|
||||
@@ -520,8 +497,7 @@ void Track::ReplaceBlock(Block *old, Block *replace)
|
||||
|
||||
emit BlockAdded(replace);
|
||||
|
||||
ignore_arraymap_++;
|
||||
SetStandardValue(kArrayMapInput, QVariant::fromValue(block_array_indexes_));
|
||||
UpdateArrayMap();
|
||||
}
|
||||
|
||||
rational Track::track_length() const
|
||||
@@ -553,6 +529,13 @@ void Track::SetLocked(bool e)
|
||||
locked_ = e;
|
||||
}
|
||||
|
||||
void Track::InputConnectedEvent(const QString &input, int element, Node *node)
|
||||
{
|
||||
if (arraymap_invalid_ && input == kBlockInput && element >= 0) {
|
||||
RefreshBlockCacheFromArrayMap();
|
||||
}
|
||||
}
|
||||
|
||||
void Track::UpdateInOutFrom(int index)
|
||||
{
|
||||
// Find block just before this one to find the last out point
|
||||
@@ -727,6 +710,46 @@ int Track::ConnectBlock(Block *b)
|
||||
}
|
||||
}
|
||||
|
||||
void Track::UpdateArrayMap()
|
||||
{
|
||||
ignore_arraymap_++;
|
||||
SetStandardValue(kArrayMapInput, QByteArray(reinterpret_cast<const char *>(block_array_indexes_.data()), block_array_indexes_.size() * sizeof(uint32_t)));
|
||||
}
|
||||
|
||||
void Track::RefreshBlockCacheFromArrayMap()
|
||||
{
|
||||
QByteArray bytes = GetStandardValue(kArrayMapInput).toByteArray();
|
||||
block_array_indexes_.resize(bytes.size() / sizeof(uint32_t));
|
||||
memcpy(block_array_indexes_.data(), bytes.data(), bytes.size());
|
||||
blocks_.clear();
|
||||
blocks_.reserve(block_array_indexes_.size());
|
||||
|
||||
Block *prev = nullptr;
|
||||
arraymap_invalid_ = false;
|
||||
|
||||
for (int i = 0; i < block_array_indexes_.size(); i++) {
|
||||
Block *b = static_cast<Block*>(GetConnectedOutput(kBlockInput, block_array_indexes_.at(i)));
|
||||
|
||||
Block::set_previous_next(prev, b);
|
||||
|
||||
if (b) {
|
||||
b->set_track(this);
|
||||
blocks_.append(b);
|
||||
prev = b;
|
||||
} else {
|
||||
block_array_indexes_.resize(i);
|
||||
arraymap_invalid_ = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (prev) {
|
||||
prev->set_next(nullptr);
|
||||
}
|
||||
|
||||
UpdateInOutFrom(0);
|
||||
}
|
||||
|
||||
void Track::BlockLengthChanged()
|
||||
{
|
||||
// Assumes sender is a Block
|
||||
|
||||
@@ -444,6 +444,7 @@ signals:
|
||||
void BlocksRefreshed();
|
||||
|
||||
protected:
|
||||
virtual void InputConnectedEvent(const QString& input, int element, Node *node) override;
|
||||
virtual void InputValueChangedEvent(const QString& input, int element) override;
|
||||
|
||||
private:
|
||||
@@ -459,10 +460,12 @@ private:
|
||||
|
||||
int ConnectBlock(Block *b);
|
||||
|
||||
void UpdateArrayMap();
|
||||
|
||||
TimeRangeList block_length_pending_invalidations_;
|
||||
|
||||
QVector<Block*> blocks_;
|
||||
QVector<int> block_array_indexes_;
|
||||
QVector<uint32_t> block_array_indexes_;
|
||||
|
||||
std::list<int> empty_inputs_;
|
||||
|
||||
@@ -477,10 +480,13 @@ private:
|
||||
Sequence *sequence_;
|
||||
|
||||
int ignore_arraymap_;
|
||||
bool arraymap_invalid_;
|
||||
|
||||
private slots:
|
||||
void BlockLengthChanged();
|
||||
|
||||
void RefreshBlockCacheFromArrayMap();
|
||||
|
||||
};
|
||||
|
||||
uint qHash(const Track::Reference& r, uint seed = 0);
|
||||
|
||||
@@ -29,6 +29,9 @@ set(OLIVE_SOURCES
|
||||
node/project/serializer/serializer211228.h
|
||||
node/project/serializer/serializer220403.cpp
|
||||
node/project/serializer/serializer220403.h
|
||||
node/project/serializer/serializer230220.cpp
|
||||
node/project/serializer/serializer230220.h
|
||||
|
||||
|
||||
node/project/serializer/typeserializer.cpp
|
||||
node/project/serializer/typeserializer.h
|
||||
|
||||
@@ -32,6 +32,7 @@
|
||||
#include "serializer210907.h"
|
||||
#include "serializer211228.h"
|
||||
#include "serializer220403.h"
|
||||
#include "serializer230220.h"
|
||||
|
||||
namespace olive {
|
||||
|
||||
@@ -48,6 +49,7 @@ void ProjectSerializer::Initialize()
|
||||
instances_.append(new ProjectSerializer210907);
|
||||
instances_.append(new ProjectSerializer211228);
|
||||
instances_.append(new ProjectSerializer220403);
|
||||
instances_.append(new ProjectSerializer230220);
|
||||
}
|
||||
|
||||
void ProjectSerializer::Destroy()
|
||||
@@ -64,9 +66,9 @@ ProjectSerializer::Result ProjectSerializer::Load(Project *project, const QStrin
|
||||
// Some project files are compressed, marked with "OVEC" at the beginning of the file. Check for
|
||||
// that signature now.
|
||||
std::unique_ptr<QXmlStreamReader> reader;
|
||||
QByteArray b = project_file.read(4);
|
||||
if (!memcmp(b.data(), "OVEC", 4)) {
|
||||
if (CheckCompressedID(&project_file)) {
|
||||
// File is compressed, decompress into memory
|
||||
QByteArray b;
|
||||
b = qUncompress(project_file.readAll());
|
||||
reader.reset(new QXmlStreamReader(b));
|
||||
} else {
|
||||
@@ -256,6 +258,12 @@ ProjectSerializer::Result ProjectSerializer::Copy(const SaveData &data, const QS
|
||||
return res;
|
||||
}
|
||||
|
||||
bool ProjectSerializer::CheckCompressedID(QFile *file)
|
||||
{
|
||||
QByteArray b = file->read(4);
|
||||
return !memcmp(b.data(), "OVEC", 4);
|
||||
}
|
||||
|
||||
bool ProjectSerializer::IsCancelled() const
|
||||
{
|
||||
return false;
|
||||
|
||||
@@ -165,6 +165,8 @@ public:
|
||||
static Result Save(QXmlStreamWriter *write_device, const SaveData &data, const QString &type);
|
||||
static Result Copy(const SaveData &data, const QString &type);
|
||||
|
||||
static bool CheckCompressedID(QFile *file);
|
||||
|
||||
protected:
|
||||
virtual LoadData Load(Project *project, QXmlStreamReader *reader, void *reserved) const = 0;
|
||||
|
||||
|
||||
@@ -156,6 +156,20 @@ ProjectSerializer210528::LoadData ProjectSerializer210528::Load(Project *project
|
||||
// Make connections
|
||||
PostConnect(xml_node_data);
|
||||
|
||||
// Resolve tracks
|
||||
for (Node *n : project->nodes()) {
|
||||
n->SetCachesEnabled(true);
|
||||
|
||||
if (Track *t = dynamic_cast<Track *>(n)) {
|
||||
for (int i = 0; i < t->InputArraySize(Track::kBlockInput); i++) {
|
||||
Block *b = static_cast<Block*>(t->GetConnectedOutput(Track::kBlockInput, i));
|
||||
if (!b->track()) {
|
||||
t->AppendBlock(b);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return LoadData();
|
||||
}
|
||||
|
||||
|
||||
@@ -156,6 +156,20 @@ ProjectSerializer210907::LoadData ProjectSerializer210907::Load(Project *project
|
||||
// Make connections
|
||||
PostConnect(xml_node_data);
|
||||
|
||||
// Resolve tracks
|
||||
for (Node *n : project->nodes()) {
|
||||
n->SetCachesEnabled(true);
|
||||
|
||||
if (Track *t = dynamic_cast<Track *>(n)) {
|
||||
for (int i = 0; i < t->InputArraySize(Track::kBlockInput); i++) {
|
||||
Block *b = static_cast<Block*>(t->GetConnectedOutput(Track::kBlockInput, i));
|
||||
if (!b->track()) {
|
||||
t->AppendBlock(b);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return LoadData();
|
||||
}
|
||||
|
||||
|
||||
@@ -205,6 +205,20 @@ ProjectSerializer211228::LoadData ProjectSerializer211228::Load(Project *project
|
||||
}
|
||||
}
|
||||
|
||||
// Resolve tracks
|
||||
for (Node *n : project->nodes()) {
|
||||
n->SetCachesEnabled(true);
|
||||
|
||||
if (Track *t = dynamic_cast<Track *>(n)) {
|
||||
for (int i = 0; i < t->InputArraySize(Track::kBlockInput); i++) {
|
||||
Block *b = static_cast<Block*>(t->GetConnectedOutput(Track::kBlockInput, i));
|
||||
if (!b->track()) {
|
||||
t->AppendBlock(b);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return load_data;
|
||||
}
|
||||
|
||||
|
||||
@@ -26,20 +26,6 @@
|
||||
|
||||
namespace olive {
|
||||
|
||||
// These wrappers may appear to do nothing, but they seem to address a bug where sometimes
|
||||
// QXmlStreamWriter would insert nonsense null characters into a project. This is probably some
|
||||
// real edge case like compiler optimization or some bullshit like that. I don't even know if it
|
||||
// affects all platforms, but it definitely affected me on Linux.
|
||||
void WriteStartElement(QXmlStreamWriter *writer, const QString &s)
|
||||
{
|
||||
writer->writeStartElement(s);
|
||||
}
|
||||
|
||||
void WriteEndElement(QXmlStreamWriter *writer)
|
||||
{
|
||||
writer->writeEndElement();
|
||||
}
|
||||
|
||||
ProjectSerializer220403::LoadData ProjectSerializer220403::Load(Project *project, QXmlStreamReader *reader, void *reserved) const
|
||||
{
|
||||
QMap<quintptr, QMap<QString, QString> > properties;
|
||||
@@ -331,164 +317,23 @@ ProjectSerializer220403::LoadData ProjectSerializer220403::Load(Project *project
|
||||
}
|
||||
}
|
||||
|
||||
// Re-enable caches
|
||||
// Re-enable caches and resolve tracks
|
||||
for (Node *n : project->nodes()) {
|
||||
n->SetCachesEnabled(true);
|
||||
|
||||
if (Track *t = dynamic_cast<Track *>(n)) {
|
||||
for (int i = 0; i < t->InputArraySize(Track::kBlockInput); i++) {
|
||||
Block *b = static_cast<Block*>(t->GetConnectedOutput(Track::kBlockInput, i));
|
||||
if (!b->track()) {
|
||||
t->AppendBlock(b);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return load_data;
|
||||
}
|
||||
|
||||
void ProjectSerializer220403::Save(QXmlStreamWriter *writer, const SaveData &data, void *reserved) const
|
||||
{
|
||||
if (!data.GetOnlySerializeMarkers().empty()) {
|
||||
|
||||
WriteStartElement(writer, QStringLiteral("markers"));
|
||||
|
||||
for (auto it=data.GetOnlySerializeMarkers().cbegin(); it!=data.GetOnlySerializeMarkers().cend(); it++) {
|
||||
TimelineMarker *marker = *it;
|
||||
|
||||
WriteStartElement(writer, QStringLiteral("marker"));
|
||||
|
||||
SaveMarker(writer, marker);
|
||||
|
||||
WriteEndElement(writer); // marker
|
||||
}
|
||||
|
||||
WriteEndElement(writer); // markers
|
||||
|
||||
} else if (!data.GetOnlySerializeKeyframes().empty()) {
|
||||
|
||||
WriteStartElement(writer, QStringLiteral("keyframes"));
|
||||
|
||||
// Organize keyframes into node+input
|
||||
QHash<QString, QHash<QString, QMap<int, QMap<int, QVector<NodeKeyframe*> > > > > organized;
|
||||
|
||||
for (auto it=data.GetOnlySerializeKeyframes().cbegin(); it!=data.GetOnlySerializeKeyframes().cend(); it++) {
|
||||
NodeKeyframe *key = *it;
|
||||
organized[key->parent()->id()][key->input()][key->element()][key->track()].append(key);
|
||||
}
|
||||
|
||||
for (auto it=organized.cbegin(); it!=organized.cend(); it++) {
|
||||
WriteStartElement(writer, QStringLiteral("node"));
|
||||
|
||||
writer->writeAttribute(QStringLiteral("id"), it.key());
|
||||
|
||||
for (auto jt=it.value().cbegin(); jt!=it.value().cend(); jt++) {
|
||||
WriteStartElement(writer, QStringLiteral("input"));
|
||||
|
||||
writer->writeAttribute(QStringLiteral("id"), jt.key());
|
||||
|
||||
for (auto kt=jt.value().cbegin(); kt!=jt.value().cend(); kt++) {
|
||||
WriteStartElement(writer, QStringLiteral("element"));
|
||||
|
||||
writer->writeAttribute(QStringLiteral("id"), QString::number(kt.key()));
|
||||
|
||||
for (auto lt=kt.value().cbegin(); lt!=kt.value().cend(); lt++) {
|
||||
const QVector<NodeKeyframe *> &keys = lt.value();
|
||||
|
||||
WriteStartElement(writer, QStringLiteral("track"));
|
||||
|
||||
writer->writeAttribute(QStringLiteral("id"), QString::number(lt.key()));
|
||||
|
||||
for (NodeKeyframe *key : keys) {
|
||||
WriteStartElement(writer, QStringLiteral("key"));
|
||||
SaveKeyframe(writer, key, key->parent()->GetInputDataType(key->input()));
|
||||
WriteEndElement(writer); // key
|
||||
}
|
||||
|
||||
WriteEndElement(writer); // track
|
||||
}
|
||||
|
||||
WriteEndElement(writer); // element
|
||||
}
|
||||
|
||||
WriteEndElement(writer); // input
|
||||
}
|
||||
|
||||
WriteEndElement(writer); // node;
|
||||
}
|
||||
|
||||
WriteEndElement(writer); // keyframes
|
||||
|
||||
} else if (Project *project = data.GetProject()) {
|
||||
|
||||
writer->writeTextElement(QStringLiteral("uuid"), project->GetUuid().toString());
|
||||
|
||||
WriteStartElement(writer, QStringLiteral("nodes"));
|
||||
|
||||
const QVector<Node*> &using_node_list = (data.GetOnlySerializeNodes().isEmpty()) ? project->nodes() : data.GetOnlySerializeNodes();
|
||||
|
||||
foreach (Node* node, using_node_list) {
|
||||
WriteStartElement(writer, QStringLiteral("node"));
|
||||
|
||||
if (node == project->root()) {
|
||||
writer->writeAttribute(QStringLiteral("root"), QStringLiteral("1"));
|
||||
} else if (node == project->color_manager()) {
|
||||
writer->writeAttribute(QStringLiteral("cm"), QStringLiteral("1"));
|
||||
} else if (node == project->settings()) {
|
||||
writer->writeAttribute(QStringLiteral("settings"), QStringLiteral("1"));
|
||||
}
|
||||
|
||||
writer->writeAttribute(QStringLiteral("id"), node->id());
|
||||
|
||||
SaveNode(node, writer);
|
||||
|
||||
WriteEndElement(writer); // node
|
||||
}
|
||||
|
||||
WriteEndElement(writer); // nodes
|
||||
|
||||
WriteStartElement(writer, QStringLiteral("positions"));
|
||||
|
||||
foreach (Node* context, using_node_list) {
|
||||
const Node::PositionMap &map = context->GetContextPositions();
|
||||
|
||||
if (!map.isEmpty()) {
|
||||
WriteStartElement(writer, QStringLiteral("context"));
|
||||
|
||||
writer->writeAttribute(QStringLiteral("ptr"), QString::number(reinterpret_cast<quintptr>(context)));
|
||||
|
||||
for (auto jt=map.cbegin(); jt!=map.cend(); jt++) {
|
||||
if (data.GetOnlySerializeNodes().isEmpty() || data.GetOnlySerializeNodes().contains(jt.key())) {
|
||||
WriteStartElement(writer, QStringLiteral("node"));
|
||||
SavePosition(writer, jt.key(), jt.value());
|
||||
WriteEndElement(writer); // node
|
||||
}
|
||||
}
|
||||
|
||||
WriteEndElement(writer); // context
|
||||
}
|
||||
}
|
||||
|
||||
WriteEndElement(writer); // positions
|
||||
|
||||
WriteStartElement(writer, QStringLiteral("properties"));
|
||||
|
||||
for (auto it=data.GetProperties().cbegin(); it!=data.GetProperties().cend(); it++) {
|
||||
WriteStartElement(writer, QStringLiteral("node"));
|
||||
|
||||
writer->writeAttribute(QStringLiteral("ptr"), QString::number(reinterpret_cast<quintptr>(it.key())));
|
||||
|
||||
for (auto jt=it.value().cbegin(); jt!=it.value().cend(); jt++) {
|
||||
writer->writeTextElement(jt.key(), jt.value());
|
||||
}
|
||||
|
||||
WriteEndElement(writer); // node
|
||||
}
|
||||
|
||||
WriteEndElement(writer); // properties
|
||||
|
||||
// Save main window project layout
|
||||
project->GetLayoutInfo().toXml(writer);
|
||||
|
||||
} else {
|
||||
|
||||
qCritical() << "Cannot save nodes without project object";
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
void ProjectSerializer220403::LoadNode(Node *node, XMLNodeData &xml_node_data, QXmlStreamReader *reader) const
|
||||
{
|
||||
while (XMLReadNextStartElement(reader)) {
|
||||
@@ -590,69 +435,6 @@ void ProjectSerializer220403::LoadNode(Node *node, XMLNodeData &xml_node_data, Q
|
||||
node->LoadFinishedEvent();
|
||||
}
|
||||
|
||||
void ProjectSerializer220403::SaveNode(Node *node, QXmlStreamWriter *writer) const
|
||||
{
|
||||
writer->writeTextElement(QStringLiteral("ptr"), QString::number(reinterpret_cast<quintptr>(node)));
|
||||
|
||||
writer->writeTextElement(QStringLiteral("label"), node->GetLabel());
|
||||
writer->writeTextElement(QStringLiteral("color"), QString::number(node->GetOverrideColor()));
|
||||
|
||||
foreach (const QString& input, node->inputs()) {
|
||||
WriteStartElement(writer, QStringLiteral("input"));
|
||||
|
||||
SaveInput(node, writer, input);
|
||||
|
||||
WriteEndElement(writer); // input
|
||||
}
|
||||
|
||||
WriteStartElement(writer, QStringLiteral("links"));
|
||||
foreach (Node* link, node->links()) {
|
||||
writer->writeTextElement(QStringLiteral("link"), QString::number(reinterpret_cast<quintptr>(link)));
|
||||
}
|
||||
WriteEndElement(writer); // links
|
||||
|
||||
WriteStartElement(writer, QStringLiteral("connections"));
|
||||
for (auto it=node->input_connections().cbegin(); it!=node->input_connections().cend(); it++) {
|
||||
WriteStartElement(writer, QStringLiteral("connection"));
|
||||
|
||||
writer->writeAttribute(QStringLiteral("input"), it->first.input());
|
||||
writer->writeAttribute(QStringLiteral("element"), QString::number(it->first.element()));
|
||||
|
||||
writer->writeTextElement(QStringLiteral("output"), QString::number(reinterpret_cast<quintptr>(it->second)));
|
||||
|
||||
WriteEndElement(writer); // connection
|
||||
}
|
||||
WriteEndElement(writer); // connections
|
||||
|
||||
WriteStartElement(writer, QStringLiteral("hints"));
|
||||
for (auto it=node->GetValueHints().cbegin(); it!=node->GetValueHints().cend(); it++) {
|
||||
WriteStartElement(writer, QStringLiteral("hint"));
|
||||
|
||||
writer->writeAttribute(QStringLiteral("input"), it.key().input);
|
||||
writer->writeAttribute(QStringLiteral("element"), QString::number(it.key().element));
|
||||
|
||||
SaveValueHint(&it.value(), writer);
|
||||
|
||||
WriteEndElement(writer); // hint
|
||||
}
|
||||
WriteEndElement(writer); // hints
|
||||
|
||||
WriteStartElement(writer, QStringLiteral("caches"));
|
||||
|
||||
writer->writeTextElement(QStringLiteral("audio"), node->audio_playback_cache()->GetUuid().toString());
|
||||
writer->writeTextElement(QStringLiteral("video"), node->video_frame_cache()->GetUuid().toString());
|
||||
writer->writeTextElement(QStringLiteral("thumb"), node->thumbnail_cache()->GetUuid().toString());
|
||||
writer->writeTextElement(QStringLiteral("waveform"), node->waveform_cache()->GetUuid().toString());
|
||||
|
||||
WriteEndElement(writer); // caches
|
||||
|
||||
WriteStartElement(writer, QStringLiteral("custom"));
|
||||
|
||||
SaveNodeCustom(writer, node);
|
||||
|
||||
WriteEndElement(writer); // custom
|
||||
}
|
||||
|
||||
void ProjectSerializer220403::LoadInput(Node *node, QXmlStreamReader *reader, XMLNodeData &xml_node_data) const
|
||||
{
|
||||
if (dynamic_cast<NodeGroup*>(node)) {
|
||||
@@ -716,33 +498,6 @@ void ProjectSerializer220403::LoadInput(Node *node, QXmlStreamReader *reader, XM
|
||||
}
|
||||
}
|
||||
|
||||
void ProjectSerializer220403::SaveInput(Node *node, QXmlStreamWriter *writer, const QString &id) const
|
||||
{
|
||||
writer->writeAttribute(QStringLiteral("id"), id);
|
||||
|
||||
WriteStartElement(writer, QStringLiteral("primary"));
|
||||
|
||||
SaveImmediate(writer, node, id, -1);
|
||||
|
||||
WriteEndElement(writer); // primary
|
||||
|
||||
WriteStartElement(writer, QStringLiteral("subelements"));
|
||||
|
||||
int arr_sz = node->InputArraySize(id);
|
||||
|
||||
writer->writeAttribute(QStringLiteral("count"), QString::number(arr_sz));
|
||||
|
||||
for (int i=0; i<arr_sz; i++) {
|
||||
WriteStartElement(writer, QStringLiteral("element"));
|
||||
|
||||
SaveImmediate(writer, node, id, i);
|
||||
|
||||
WriteEndElement(writer); // element
|
||||
}
|
||||
|
||||
WriteEndElement(writer); // subelements
|
||||
}
|
||||
|
||||
void ProjectSerializer220403::LoadImmediate(QXmlStreamReader *reader, Node *node, const QString& input, int element, XMLNodeData &xml_node_data) const
|
||||
{
|
||||
Q_UNUSED(xml_node_data)
|
||||
@@ -840,61 +595,6 @@ void ProjectSerializer220403::LoadImmediate(QXmlStreamReader *reader, Node *node
|
||||
}
|
||||
}
|
||||
|
||||
void ProjectSerializer220403::SaveImmediate(QXmlStreamWriter *writer, Node *node, const QString& input, int element) const
|
||||
{
|
||||
if (node->IsInputKeyframable(input)) {
|
||||
writer->writeTextElement(QStringLiteral("keyframing"), QString::number(node->IsInputKeyframing(input, element)));
|
||||
}
|
||||
|
||||
NodeValue::Type data_type = node->GetInputDataType(input);
|
||||
|
||||
// Write standard value
|
||||
WriteStartElement(writer, QStringLiteral("standard"));
|
||||
|
||||
foreach (const QVariant& v, node->GetSplitStandardValue(input, element)) {
|
||||
WriteStartElement(writer, QStringLiteral("track"));
|
||||
|
||||
if (data_type == NodeValue::kVideoParams) {
|
||||
v.value<VideoParams>().Save(writer);
|
||||
} else if (data_type == NodeValue::kAudioParams) {
|
||||
TypeSerializer::SaveAudioParams(writer, v.value<AudioParams>());
|
||||
} else {
|
||||
writer->writeCharacters(NodeValue::ValueToString(data_type, v, true));
|
||||
}
|
||||
|
||||
WriteEndElement(writer); // track
|
||||
}
|
||||
|
||||
WriteEndElement(writer); // standard
|
||||
|
||||
// Write keyframes
|
||||
WriteStartElement(writer, QStringLiteral("keyframes"));
|
||||
|
||||
for (const NodeKeyframeTrack& track : node->GetKeyframeTracks(input, element)) {
|
||||
WriteStartElement(writer, QStringLiteral("track"));
|
||||
|
||||
for (NodeKeyframe* key : track) {
|
||||
WriteStartElement(writer, QStringLiteral("key"));
|
||||
|
||||
SaveKeyframe(writer, key, data_type);
|
||||
|
||||
WriteEndElement(writer); // key
|
||||
}
|
||||
|
||||
WriteEndElement(writer); // track
|
||||
}
|
||||
|
||||
WriteEndElement(writer); // keyframes
|
||||
|
||||
if (data_type == NodeValue::kColor) {
|
||||
// Save color management information
|
||||
writer->writeTextElement(QStringLiteral("csinput"), node->GetInputProperty(input, QStringLiteral("col_input")).toString());
|
||||
writer->writeTextElement(QStringLiteral("csdisplay"), node->GetInputProperty(input, QStringLiteral("col_display")).toString());
|
||||
writer->writeTextElement(QStringLiteral("csview"), node->GetInputProperty(input, QStringLiteral("col_view")).toString());
|
||||
writer->writeTextElement(QStringLiteral("cslook"), node->GetInputProperty(input, QStringLiteral("col_look")).toString());
|
||||
}
|
||||
}
|
||||
|
||||
void ProjectSerializer220403::LoadKeyframe(QXmlStreamReader *reader, NodeKeyframe *key, NodeValue::Type data_type) const
|
||||
{
|
||||
QString key_input;
|
||||
@@ -929,19 +629,6 @@ void ProjectSerializer220403::LoadKeyframe(QXmlStreamReader *reader, NodeKeyfram
|
||||
key->set_bezier_control_out(key_out_handle);
|
||||
}
|
||||
|
||||
void ProjectSerializer220403::SaveKeyframe(QXmlStreamWriter *writer, NodeKeyframe *key, NodeValue::Type data_type) const
|
||||
{
|
||||
writer->writeAttribute(QStringLiteral("input"), key->input());
|
||||
writer->writeAttribute(QStringLiteral("time"), QString::fromStdString(key->time().toString()));
|
||||
writer->writeAttribute(QStringLiteral("type"), QString::number(key->type()));
|
||||
writer->writeAttribute(QStringLiteral("inhandlex"), QString::number(key->bezier_control_in().x()));
|
||||
writer->writeAttribute(QStringLiteral("inhandley"), QString::number(key->bezier_control_in().y()));
|
||||
writer->writeAttribute(QStringLiteral("outhandlex"), QString::number(key->bezier_control_out().x()));
|
||||
writer->writeAttribute(QStringLiteral("outhandley"), QString::number(key->bezier_control_out().y()));
|
||||
|
||||
writer->writeCharacters(NodeValue::ValueToString(data_type, key->value(), true));
|
||||
}
|
||||
|
||||
bool ProjectSerializer220403::LoadPosition(QXmlStreamReader *reader, quintptr *node_ptr, Node::Position *pos) const
|
||||
{
|
||||
bool got_node_ptr = false;
|
||||
@@ -973,15 +660,6 @@ bool ProjectSerializer220403::LoadPosition(QXmlStreamReader *reader, quintptr *n
|
||||
return got_node_ptr && got_pos_x && got_pos_y;
|
||||
}
|
||||
|
||||
void ProjectSerializer220403::SavePosition(QXmlStreamWriter *writer, Node *node, const Node::Position &pos) const
|
||||
{
|
||||
writer->writeAttribute(QStringLiteral("ptr"), QString::number(reinterpret_cast<quintptr>(node)));
|
||||
|
||||
writer->writeTextElement(QStringLiteral("x"), QString::number(pos.position.x()));
|
||||
writer->writeTextElement(QStringLiteral("y"), QString::number(pos.position.y()));
|
||||
writer->writeTextElement(QStringLiteral("expanded"), QString::number(pos.expanded));
|
||||
}
|
||||
|
||||
void ProjectSerializer220403::PostConnect(const XMLNodeData &xml_node_data) const
|
||||
{
|
||||
foreach (const XMLNodeData::SerializedConnection& con, xml_node_data.desired_connections) {
|
||||
@@ -1125,63 +803,6 @@ void ProjectSerializer220403::LoadNodeCustom(QXmlStreamReader *reader, Node *nod
|
||||
}
|
||||
}
|
||||
|
||||
void ProjectSerializer220403::SaveNodeCustom(QXmlStreamWriter *writer, Node *node) const
|
||||
{
|
||||
if (ViewerOutput *viewer = dynamic_cast<ViewerOutput*>(node)) {
|
||||
// Write TimelinePoints
|
||||
WriteStartElement(writer, QStringLiteral("points"));
|
||||
SaveTimelinePoints(writer, viewer);
|
||||
WriteEndElement(writer); // points
|
||||
|
||||
if (Footage *footage = dynamic_cast<Footage*>(node)) {
|
||||
writer->writeTextElement(QStringLiteral("timestamp"), QString::number(footage->timestamp()));
|
||||
}
|
||||
} else if (Track *track = dynamic_cast<Track*>(node)) {
|
||||
writer->writeTextElement(QStringLiteral("height"), QString::number(track->GetTrackHeight()));
|
||||
} else if (NodeGroup *group = dynamic_cast<NodeGroup*>(node)) {
|
||||
WriteStartElement(writer, QStringLiteral("inputpassthroughs"));
|
||||
|
||||
foreach (const NodeGroup::InputPassthrough &ip, group->GetInputPassthroughs()) {
|
||||
WriteStartElement(writer, QStringLiteral("inputpassthrough"));
|
||||
|
||||
// Reference to inner input
|
||||
writer->writeTextElement(QStringLiteral("node"), QString::number(reinterpret_cast<quintptr>(ip.second.node())));
|
||||
writer->writeTextElement(QStringLiteral("input"), ip.second.input());
|
||||
writer->writeTextElement(QStringLiteral("element"), QString::number(ip.second.element()));
|
||||
|
||||
// ID of passthrough
|
||||
writer->writeTextElement(QStringLiteral("id"), ip.first);
|
||||
|
||||
// Passthrough-specific details
|
||||
NodeInput group_input(group, ip.first, ip.second.element());
|
||||
writer->writeTextElement(QStringLiteral("name"), group->Node::GetInputName(ip.first));
|
||||
|
||||
writer->writeTextElement(QStringLiteral("flags"), QString::number((group_input.GetFlags() & ~ip.second.GetFlags()).value()));
|
||||
|
||||
NodeValue::Type data_type = group_input.GetDataType();
|
||||
writer->writeTextElement(QStringLiteral("type"), NodeValue::GetDataTypeName(data_type));
|
||||
|
||||
writer->writeTextElement(QStringLiteral("default"), NodeValue::ValueToString(data_type, group_input.GetDefaultValue(), false));
|
||||
|
||||
WriteStartElement(writer, QStringLiteral("properties"));
|
||||
auto p = group_input.GetProperties();
|
||||
for (auto it=p.cbegin(); it!=p.cend(); it++) {
|
||||
WriteStartElement(writer, QStringLiteral("property"));
|
||||
writer->writeTextElement(QStringLiteral("key"), it.key());
|
||||
writer->writeTextElement(QStringLiteral("value"), it.value().toString());
|
||||
WriteEndElement(writer); // property
|
||||
}
|
||||
WriteEndElement(writer); // properties
|
||||
|
||||
WriteEndElement(writer); // input
|
||||
}
|
||||
|
||||
WriteEndElement(writer); // inputpassthroughs
|
||||
|
||||
writer->writeTextElement(QStringLiteral("outputpassthrough"), QString::number(reinterpret_cast<quintptr>(group->GetOutputPassthrough())));
|
||||
}
|
||||
}
|
||||
|
||||
void ProjectSerializer220403::LoadTimelinePoints(QXmlStreamReader *reader, ViewerOutput *viewer) const
|
||||
{
|
||||
while (XMLReadNextStartElement(reader)) {
|
||||
@@ -1195,17 +816,6 @@ void ProjectSerializer220403::LoadTimelinePoints(QXmlStreamReader *reader, Viewe
|
||||
}
|
||||
}
|
||||
|
||||
void ProjectSerializer220403::SaveTimelinePoints(QXmlStreamWriter *writer, ViewerOutput *viewer) const
|
||||
{
|
||||
WriteStartElement(writer, QStringLiteral("workarea"));
|
||||
SaveWorkArea(writer, viewer->GetWorkArea());
|
||||
WriteEndElement(writer); // workarea
|
||||
|
||||
WriteStartElement(writer, QStringLiteral("markers"));
|
||||
SaveMarkerList(writer, viewer->GetMarkers());
|
||||
WriteEndElement(writer); // markers
|
||||
}
|
||||
|
||||
void ProjectSerializer220403::LoadMarker(QXmlStreamReader *reader, TimelineMarker *marker) const
|
||||
{
|
||||
rational in, out;
|
||||
@@ -1228,14 +838,6 @@ void ProjectSerializer220403::LoadMarker(QXmlStreamReader *reader, TimelineMarke
|
||||
reader->skipCurrentElement();
|
||||
}
|
||||
|
||||
void ProjectSerializer220403::SaveMarker(QXmlStreamWriter *writer, TimelineMarker *marker) const
|
||||
{
|
||||
writer->writeAttribute(QStringLiteral("name"), marker->name());
|
||||
writer->writeAttribute(QStringLiteral("in"), QString::fromStdString(marker->time().in().toString()));
|
||||
writer->writeAttribute(QStringLiteral("out"), QString::fromStdString(marker->time().out().toString()));
|
||||
writer->writeAttribute(QStringLiteral("color"), QString::number(marker->color()));
|
||||
}
|
||||
|
||||
void ProjectSerializer220403::LoadWorkArea(QXmlStreamReader *reader, TimelineWorkArea *workarea) const
|
||||
{
|
||||
rational range_in = workarea->in();
|
||||
@@ -1260,13 +862,6 @@ void ProjectSerializer220403::LoadWorkArea(QXmlStreamReader *reader, TimelineWor
|
||||
reader->skipCurrentElement();
|
||||
}
|
||||
|
||||
void ProjectSerializer220403::SaveWorkArea(QXmlStreamWriter *writer, TimelineWorkArea *workarea) const
|
||||
{
|
||||
writer->writeAttribute(QStringLiteral("enabled"), QString::number(workarea->enabled()));
|
||||
writer->writeAttribute(QStringLiteral("in"), QString::fromStdString(workarea->in().toString()));
|
||||
writer->writeAttribute(QStringLiteral("out"), QString::fromStdString(workarea->out().toString()));
|
||||
}
|
||||
|
||||
void ProjectSerializer220403::LoadMarkerList(QXmlStreamReader *reader, TimelineMarkerList *markers) const
|
||||
{
|
||||
while (XMLReadNextStartElement(reader)) {
|
||||
@@ -1279,19 +874,6 @@ void ProjectSerializer220403::LoadMarkerList(QXmlStreamReader *reader, TimelineM
|
||||
}
|
||||
}
|
||||
|
||||
void ProjectSerializer220403::SaveMarkerList(QXmlStreamWriter *writer, TimelineMarkerList *markers) const
|
||||
{
|
||||
for (auto it=markers->cbegin(); it!=markers->cend(); it++) {
|
||||
TimelineMarker* marker = *it;
|
||||
|
||||
WriteStartElement(writer, QStringLiteral("marker"));
|
||||
|
||||
SaveMarker(writer, marker);
|
||||
|
||||
WriteEndElement(writer); // marker
|
||||
}
|
||||
}
|
||||
|
||||
void ProjectSerializer220403::LoadValueHint(Node::ValueHint *hint, QXmlStreamReader *reader) const
|
||||
{
|
||||
QVector<NodeValue::Type> types;
|
||||
@@ -1317,19 +899,4 @@ void ProjectSerializer220403::LoadValueHint(Node::ValueHint *hint, QXmlStreamRea
|
||||
hint->set_type(types);
|
||||
}
|
||||
|
||||
void ProjectSerializer220403::SaveValueHint(const Node::ValueHint *hint, QXmlStreamWriter *writer) const
|
||||
{
|
||||
WriteStartElement(writer, QStringLiteral("types"));
|
||||
|
||||
for (auto it=hint->types().cbegin(); it!=hint->types().cend(); it++) {
|
||||
writer->writeTextElement(QStringLiteral("type"), QString::number(*it));
|
||||
}
|
||||
|
||||
WriteEndElement(writer); // types
|
||||
|
||||
writer->writeTextElement(QStringLiteral("index"), QString::number(hint->index()));
|
||||
|
||||
writer->writeTextElement(QStringLiteral("tag"), hint->tag());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -33,8 +33,6 @@ public:
|
||||
protected:
|
||||
virtual LoadData Load(Project *project, QXmlStreamReader *reader, void *reserved) const override;
|
||||
|
||||
virtual void Save(QXmlStreamWriter *writer, const SaveData &data, void *reserved) const override;
|
||||
|
||||
virtual uint Version() const override
|
||||
{
|
||||
return 220403;
|
||||
@@ -76,50 +74,28 @@ private:
|
||||
|
||||
void LoadNode(Node *node, XMLNodeData &xml_node_data, QXmlStreamReader *reader) const;
|
||||
|
||||
void SaveNode(Node *node, QXmlStreamWriter *writer) const;
|
||||
|
||||
void LoadInput(Node *node, QXmlStreamReader* reader, XMLNodeData &xml_node_data) const;
|
||||
|
||||
void SaveInput(Node *node, QXmlStreamWriter* writer, const QString& id) const;
|
||||
|
||||
void LoadImmediate(QXmlStreamReader *reader, Node *node, const QString& input, int element, XMLNodeData& xml_node_data) const;
|
||||
|
||||
void SaveImmediate(QXmlStreamWriter *writer, Node *node, const QString &input, int element) const;
|
||||
|
||||
void LoadKeyframe(QXmlStreamReader *reader, NodeKeyframe *key, NodeValue::Type data_type) const;
|
||||
|
||||
void SaveKeyframe(QXmlStreamWriter *writer, NodeKeyframe *key, NodeValue::Type data_type) const;
|
||||
|
||||
bool LoadPosition(QXmlStreamReader *reader, quintptr *node_ptr, Node::Position *pos) const;
|
||||
|
||||
void SavePosition(QXmlStreamWriter *writer, Node *node, const Node::Position &pos) const;
|
||||
|
||||
void PostConnect(const XMLNodeData &xml_node_data) const;
|
||||
|
||||
void LoadNodeCustom(QXmlStreamReader *reader, Node *node, XMLNodeData &xml_node_data) const;
|
||||
|
||||
void SaveNodeCustom(QXmlStreamWriter *writer, Node *node) const;
|
||||
|
||||
void LoadTimelinePoints(QXmlStreamReader *reader, ViewerOutput *viewer) const;
|
||||
|
||||
void SaveTimelinePoints(QXmlStreamWriter *writer, ViewerOutput *viewer) const;
|
||||
|
||||
void LoadMarker(QXmlStreamReader *reader, TimelineMarker *marker) const;
|
||||
|
||||
void SaveMarker(QXmlStreamWriter *writer, TimelineMarker *marker) const;
|
||||
|
||||
void LoadWorkArea(QXmlStreamReader *reader, TimelineWorkArea *workarea) const;
|
||||
|
||||
void SaveWorkArea(QXmlStreamWriter *writer, TimelineWorkArea *workarea) const;
|
||||
|
||||
void LoadMarkerList(QXmlStreamReader *reader, TimelineMarkerList *markers) const;
|
||||
|
||||
void SaveMarkerList(QXmlStreamWriter *writer, TimelineMarkerList *markers) const;
|
||||
|
||||
void LoadValueHint(Node::ValueHint *hint, QXmlStreamReader *reader) const;
|
||||
|
||||
void SaveValueHint(const Node::ValueHint *hint, QXmlStreamWriter *writer) const;
|
||||
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,127 @@
|
||||
/***
|
||||
|
||||
Olive - Non-Linear Video Editor
|
||||
Copyright (C) 2023 Olive Studios LLC
|
||||
|
||||
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/>.
|
||||
|
||||
***/
|
||||
|
||||
#ifndef PROJECTSERIALIZER230220_H
|
||||
#define PROJECTSERIALIZER230220_H
|
||||
|
||||
#include "serializer.h"
|
||||
|
||||
namespace olive {
|
||||
|
||||
class ProjectSerializer230220 : public ProjectSerializer
|
||||
{
|
||||
public:
|
||||
ProjectSerializer230220() = default;
|
||||
|
||||
protected:
|
||||
virtual LoadData Load(Project *project, QXmlStreamReader *reader, void *reserved) const override;
|
||||
|
||||
virtual void Save(QXmlStreamWriter *writer, const SaveData &data, void *reserved) const override;
|
||||
|
||||
virtual uint Version() const override
|
||||
{
|
||||
return 230220;
|
||||
}
|
||||
|
||||
private:
|
||||
struct XMLNodeData {
|
||||
struct SerializedConnection {
|
||||
NodeInput input;
|
||||
quintptr output_node;
|
||||
};
|
||||
|
||||
struct BlockLink {
|
||||
Node* block;
|
||||
quintptr link;
|
||||
};
|
||||
|
||||
struct GroupLink {
|
||||
NodeGroup *group;
|
||||
QString passthrough_id;
|
||||
quintptr input_node;
|
||||
QString input_id;
|
||||
int input_element;
|
||||
QString custom_name;
|
||||
InputFlags custom_flags;
|
||||
NodeValue::Type data_type;
|
||||
QVariant default_val;
|
||||
QHash<QString, QVariant> custom_properties;
|
||||
};
|
||||
|
||||
QHash<quintptr, Node*> node_ptrs;
|
||||
QList<SerializedConnection> desired_connections;
|
||||
QList<BlockLink> block_links;
|
||||
QVector<GroupLink> group_input_links;
|
||||
QHash<NodeGroup*, quintptr> group_output_links;
|
||||
QHash<Node*, QUuid> node_uuids;
|
||||
|
||||
};
|
||||
|
||||
void LoadNode(Node *node, XMLNodeData &xml_node_data, QXmlStreamReader *reader) const;
|
||||
|
||||
void SaveNode(Node *node, QXmlStreamWriter *writer) const;
|
||||
|
||||
void LoadInput(Node *node, QXmlStreamReader* reader, XMLNodeData &xml_node_data) const;
|
||||
|
||||
void SaveInput(Node *node, QXmlStreamWriter* writer, const QString& id) const;
|
||||
|
||||
void LoadImmediate(QXmlStreamReader *reader, Node *node, const QString& input, int element, XMLNodeData& xml_node_data) const;
|
||||
|
||||
void SaveImmediate(QXmlStreamWriter *writer, Node *node, const QString &input, int element) const;
|
||||
|
||||
void LoadKeyframe(QXmlStreamReader *reader, NodeKeyframe *key, NodeValue::Type data_type) const;
|
||||
|
||||
void SaveKeyframe(QXmlStreamWriter *writer, NodeKeyframe *key, NodeValue::Type data_type) const;
|
||||
|
||||
bool LoadPosition(QXmlStreamReader *reader, quintptr *node_ptr, Node::Position *pos) const;
|
||||
|
||||
void SavePosition(QXmlStreamWriter *writer, Node *node, const Node::Position &pos) const;
|
||||
|
||||
void PostConnect(const XMLNodeData &xml_node_data) const;
|
||||
|
||||
void LoadNodeCustom(QXmlStreamReader *reader, Node *node, XMLNodeData &xml_node_data) const;
|
||||
|
||||
void SaveNodeCustom(QXmlStreamWriter *writer, Node *node) const;
|
||||
|
||||
void LoadTimelinePoints(QXmlStreamReader *reader, ViewerOutput *viewer) const;
|
||||
|
||||
void SaveTimelinePoints(QXmlStreamWriter *writer, ViewerOutput *viewer) const;
|
||||
|
||||
void LoadMarker(QXmlStreamReader *reader, TimelineMarker *marker) const;
|
||||
|
||||
void SaveMarker(QXmlStreamWriter *writer, TimelineMarker *marker) const;
|
||||
|
||||
void LoadWorkArea(QXmlStreamReader *reader, TimelineWorkArea *workarea) const;
|
||||
|
||||
void SaveWorkArea(QXmlStreamWriter *writer, TimelineWorkArea *workarea) const;
|
||||
|
||||
void LoadMarkerList(QXmlStreamReader *reader, TimelineMarkerList *markers) const;
|
||||
|
||||
void SaveMarkerList(QXmlStreamWriter *writer, TimelineMarkerList *markers) const;
|
||||
|
||||
void LoadValueHint(Node::ValueHint *hint, QXmlStreamReader *reader) const;
|
||||
|
||||
void SaveValueHint(const Node::ValueHint *hint, QXmlStreamWriter *writer) const;
|
||||
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
#endif // PROJECTSERIALIZER230220_H
|
||||
@@ -77,6 +77,8 @@ QString NodeValue::ValueToString(Type data_type, const QVariant &value, bool val
|
||||
return QString();
|
||||
} else if (data_type == kInt) {
|
||||
return QString::number(value.value<int64_t>());
|
||||
} else if (data_type == kBinary) {
|
||||
return value.toByteArray().toBase64();
|
||||
} else {
|
||||
if (value.canConvert<QString>()) {
|
||||
return value.toString();
|
||||
@@ -243,6 +245,8 @@ QVariant NodeValue::StringToValue(Type data_type, const QString &string, bool va
|
||||
return QVariant::fromValue(string.toLongLong());
|
||||
} else if (data_type == kRational) {
|
||||
return QVariant::fromValue(rational::fromString(string.toStdString()));
|
||||
} else if (data_type == kBinary) {
|
||||
return QByteArray::fromBase64(string.toLatin1());
|
||||
} else {
|
||||
return string;
|
||||
}
|
||||
@@ -297,6 +301,8 @@ QString NodeValue::GetPrettyDataTypeName(Type type)
|
||||
return QCoreApplication::translate("NodeValue", "Audio Parameters");
|
||||
case kSubtitleParams:
|
||||
return QCoreApplication::translate("NodeValue", "Subtitle Parameters");
|
||||
case kBinary:
|
||||
return QCoreApplication::translate("NodeValue", "Binary");
|
||||
|
||||
case kDataTypeCount:
|
||||
break;
|
||||
@@ -348,6 +354,8 @@ QString NodeValue::GetDataTypeName(Type type)
|
||||
return QStringLiteral("aparam");
|
||||
case kSubtitleParams:
|
||||
return QStringLiteral("sparam");
|
||||
case kBinary:
|
||||
return QStringLiteral("binary");
|
||||
case kDataTypeCount:
|
||||
break;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user