Implement applying changed track meta-data for Mkv

This commit is contained in:
Martchus 2017-06-11 22:57:28 +02:00
parent b4de493b56
commit 9b0d74b6ad
4 changed files with 88 additions and 13 deletions

View File

@ -63,6 +63,7 @@ public:
const char *mediaTypeName() const;
uint64 size() const;
uint32 trackNumber() const;
void setTrackNumber(uint32 trackNumber);
uint64 id() const;
void setId(uint64 id);
const std::string name() const;
@ -322,6 +323,15 @@ inline uint32 AbstractTrack::trackNumber() const
return m_trackNumber;
}
/*!
* \brief Sets the track number.
* \remarks Whether the new value is applied when saving changes depends on the implementation.
*/
inline void AbstractTrack::setTrackNumber(uint32 trackNumber)
{
m_trackNumber = trackNumber;
}
/*!
* \brief Returns the track ID if known; otherwise returns 0.
*/

View File

@ -471,17 +471,39 @@ void MatroskaTrack::internalParseHeader()
* \sa See MatroskaTrack::prepareMakingHeader() for more information.
*/
MatroskaTrackHeaderMaker::MatroskaTrackHeaderMaker(const MatroskaTrack &track) :
m_track(track)
m_track(track),
m_dataSize(0)
{
m_track.m_trackElement->makeBuffer();
}
/*!
* \brief Returns the associated tag.
*/
uint64 MatroskaTrackHeaderMaker::requiredSize() const
{
return m_track.m_trackElement->totalSize();
for(EbmlElement *trackInfoElement = m_track.m_trackElement->firstChild(); trackInfoElement; trackInfoElement = trackInfoElement->nextSibling()) {
switch(trackInfoElement->id()) {
case MatroskaIds::TrackNumber:
m_dataSize += 1 + 1 + EbmlElement::calculateUIntegerLength(m_track.trackNumber());
break;
case MatroskaIds::TrackUID:
m_dataSize += 2 + 1 + EbmlElement::calculateUIntegerLength(m_track.id());
break;
case MatroskaIds::TrackName:
m_dataSize += 2 + EbmlElement::calculateSizeDenotationLength(m_track.name().size()) + m_track.name().size();
break;
case MatroskaIds::TrackLanguage:
m_dataSize += 3 + EbmlElement::calculateSizeDenotationLength(m_track.language().size()) + m_track.language().size();
break;
case MatroskaIds::TrackFlagEnabled:
m_dataSize += 1 + 1 + EbmlElement::calculateUIntegerLength(m_track.isEnabled());
break;
case MatroskaIds::TrackFlagDefault:
m_dataSize += 1 + 1 + EbmlElement::calculateUIntegerLength(m_track.isDefault());
break;
case MatroskaIds::TrackFlagForced:
m_dataSize += 2 + 1 + EbmlElement::calculateUIntegerLength(m_track.isForced());
break;
default:
trackInfoElement->makeBuffer();
m_dataSize += trackInfoElement->totalSize();
}
}
m_sizeDenotationLength = EbmlElement::calculateSizeDenotationLength(m_dataSize);
m_requiredSize = 2 + m_sizeDenotationLength + m_dataSize;
}
/*!
@ -493,7 +515,40 @@ uint64 MatroskaTrackHeaderMaker::requiredSize() const
*/
void MatroskaTrackHeaderMaker::make(ostream &stream) const
{
m_track.m_trackElement->copyBuffer(stream);
// make ID and size
char buffer[10];
BE::getBytes(static_cast<uint16>(MatroskaIds::TrackEntry), buffer);
EbmlElement::makeSizeDenotation(m_dataSize, buffer + 2);
stream.write(buffer, 2 + m_sizeDenotationLength);
// make child elements
for(EbmlElement *trackInfoElement = m_track.m_trackElement->firstChild(); trackInfoElement; trackInfoElement = trackInfoElement->nextSibling()) {
switch(trackInfoElement->id()) {
case MatroskaIds::TrackNumber:
EbmlElement::makeSimpleElement(stream, MatroskaIds::TrackNumber, m_track.trackNumber());
break;
case MatroskaIds::TrackUID:
EbmlElement::makeSimpleElement(stream, MatroskaIds::TrackUID, m_track.id());
break;
case MatroskaIds::TrackName:
EbmlElement::makeSimpleElement(stream, MatroskaIds::TrackName, m_track.name());
break;
case MatroskaIds::TrackLanguage:
EbmlElement::makeSimpleElement(stream, MatroskaIds::TrackLanguage, m_track.language());
break;
case MatroskaIds::TrackFlagEnabled:
EbmlElement::makeSimpleElement(stream, MatroskaIds::TrackFlagEnabled, m_track.isEnabled());
break;
case MatroskaIds::TrackFlagDefault:
EbmlElement::makeSimpleElement(stream, MatroskaIds::TrackFlagDefault, m_track.isDefault());
break;
case MatroskaIds::TrackFlagForced:
EbmlElement::makeSimpleElement(stream, MatroskaIds::TrackFlagForced, m_track.isForced());
break;
default:
trackInfoElement->copyBuffer(stream);
}
}
}
}

View File

@ -22,6 +22,9 @@ private:
MatroskaTrackHeaderMaker(const MatroskaTrack &track);
const MatroskaTrack &m_track;
uint64 m_dataSize;
uint64 m_requiredSize;
byte m_sizeDenotationLength;
};
/*!
@ -32,6 +35,14 @@ inline const MatroskaTrack &MatroskaTrackHeaderMaker::track() const
return m_track;
}
/*!
* \brief Returns the number of bytes which will be written when calling make().
*/
inline uint64 MatroskaTrackHeaderMaker::requiredSize() const
{
return m_requiredSize;
}
class TAG_PARSER_EXPORT MatroskaTrack : public AbstractTrack
{
friend class MatroskaContainer;

View File

@ -174,8 +174,7 @@ void OverallTests::checkMkvTestfile4()
break;
case TagStatus::TestMetaDataPresent:
// not implemented yet, so currently still undefined instead of German
CPPUNIT_ASSERT_EQUAL("und"s, track->language());
//CPPUNIT_ASSERT_EQUAL("ger"s, track->language());
CPPUNIT_ASSERT_EQUAL("ger"s, track->language());
break;
}
break;