mirror of
https://github.com/telegramdesktop/tdesktop
synced 2025-01-11 17:29:46 +00:00
Fix seek to video end.
This commit is contained in:
parent
9785ff4be6
commit
be495c17bc
@ -69,28 +69,40 @@ bool AudioTrack::tryReadFirstFrame(Packet &&packet) {
|
|||||||
if (ProcessPacket(_stream, std::move(packet)).failed()) {
|
if (ProcessPacket(_stream, std::move(packet)).failed()) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
if (const auto error = ReadNextFrame(_stream)) {
|
while (true) {
|
||||||
if (error.code() == AVERROR_EOF) {
|
if (const auto error = ReadNextFrame(_stream)) {
|
||||||
// Return the last valid frame if we seek too far.
|
if (error.code() == AVERROR_EOF) {
|
||||||
return processFirstFrame();
|
if (!_initialSkippingFrame) {
|
||||||
} else if (error.code() != AVERROR(EAGAIN) || _noMoreData) {
|
return false;
|
||||||
|
}
|
||||||
|
// Return the last valid frame if we seek too far.
|
||||||
|
_stream.frame = std::move(_initialSkippingFrame);
|
||||||
|
return processFirstFrame();
|
||||||
|
} else if (error.code() != AVERROR(EAGAIN) || _noMoreData) {
|
||||||
|
return false;
|
||||||
|
} else {
|
||||||
|
// Waiting for more packets.
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
} else if (!fillStateFromFrame()) {
|
||||||
return false;
|
return false;
|
||||||
} else {
|
} else if (_startedPosition >= _options.position) {
|
||||||
// Waiting for more packets.
|
return processFirstFrame();
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
} else if (!fillStateFromFrame()) {
|
|
||||||
return false;
|
|
||||||
} else if (_startedPosition < _options.position) {
|
|
||||||
// Seek was with AVSEEK_FLAG_BACKWARD so first we get old frames.
|
// Seek was with AVSEEK_FLAG_BACKWARD so first we get old frames.
|
||||||
// Try skipping frames until one is after the requested position.
|
// Try skipping frames until one is after the requested position.
|
||||||
return true;
|
std::swap(_initialSkippingFrame, _stream.frame);
|
||||||
} else {
|
if (!_stream.frame) {
|
||||||
return processFirstFrame();
|
_stream.frame = MakeFramePointer();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
bool AudioTrack::processFirstFrame() {
|
bool AudioTrack::processFirstFrame() {
|
||||||
|
if (!FrameHasData(_stream.frame.get())) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
mixerInit();
|
mixerInit();
|
||||||
callReady();
|
callReady();
|
||||||
return true;
|
return true;
|
||||||
|
@ -98,6 +98,9 @@ private:
|
|||||||
bool _queued = false;
|
bool _queued = false;
|
||||||
base::ConcurrentTimer _readFramesTimer;
|
base::ConcurrentTimer _readFramesTimer;
|
||||||
|
|
||||||
|
// For initial frame skipping for an exact seek.
|
||||||
|
FramePointer _initialSkippingFrame;
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
VideoTrackObject::VideoTrackObject(
|
VideoTrackObject::VideoTrackObject(
|
||||||
@ -349,25 +352,33 @@ bool VideoTrackObject::tryReadFirstFrame(Packet &&packet) {
|
|||||||
if (ProcessPacket(_stream, std::move(packet)).failed()) {
|
if (ProcessPacket(_stream, std::move(packet)).failed()) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
auto frame = QImage();
|
while (true) {
|
||||||
if (const auto error = ReadNextFrame(_stream)) {
|
if (const auto error = ReadNextFrame(_stream)) {
|
||||||
if (error.code() == AVERROR_EOF) {
|
if (error.code() == AVERROR_EOF) {
|
||||||
// Return the last valid frame if we seek too far.
|
if (!_initialSkippingFrame) {
|
||||||
return processFirstFrame();
|
return false;
|
||||||
} else if (error.code() != AVERROR(EAGAIN) || _noMoreData) {
|
}
|
||||||
|
// Return the last valid frame if we seek too far.
|
||||||
|
_stream.frame = std::move(_initialSkippingFrame);
|
||||||
|
return processFirstFrame();
|
||||||
|
} else if (error.code() != AVERROR(EAGAIN) || _noMoreData) {
|
||||||
|
return false;
|
||||||
|
} else {
|
||||||
|
// Waiting for more packets.
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
} else if (!fillStateFromFrame()) {
|
||||||
return false;
|
return false;
|
||||||
} else {
|
} else if (_syncTimePoint.trackTime >= _options.position) {
|
||||||
// Waiting for more packets.
|
return processFirstFrame();
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
} else if (!fillStateFromFrame()) {
|
|
||||||
return false;
|
|
||||||
} else if (_syncTimePoint.trackTime < _options.position) {
|
|
||||||
// Seek was with AVSEEK_FLAG_BACKWARD so first we get old frames.
|
// Seek was with AVSEEK_FLAG_BACKWARD so first we get old frames.
|
||||||
// Try skipping frames until one is after the requested position.
|
// Try skipping frames until one is after the requested position.
|
||||||
return true;
|
std::swap(_initialSkippingFrame, _stream.frame);
|
||||||
} else {
|
if (!_stream.frame) {
|
||||||
return processFirstFrame();
|
_stream.frame = MakeFramePointer();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -382,9 +393,7 @@ bool VideoTrackObject::processFirstFrame() {
|
|||||||
}
|
}
|
||||||
_shared->init(std::move(frame), _syncTimePoint.trackTime);
|
_shared->init(std::move(frame), _syncTimePoint.trackTime);
|
||||||
callReady();
|
callReady();
|
||||||
if (!_stream.queue.empty()) {
|
queueReadFrames();
|
||||||
queueReadFrames();
|
|
||||||
}
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user