1
Fork 0
mirror of https://github.com/RGBCube/serenity synced 2025-05-31 12:28:12 +00:00
Commit graph

129 commits

Author SHA1 Message Date
Zaggy1024
713b48cfe2 LibVideo/VP9: Remove unused parser field m_is_compound 2022-11-30 08:28:30 +01:00
Zaggy1024
eafc048101 LibVideo/VP9: Remove a FIXME that is impossible to fix
We can't memset an array with 32-bit integers to non-zero values,
silly past me :^)
2022-11-30 08:28:30 +01:00
Zaggy1024
5f7099cff6 LibVideo/VP9: Apply higher optimization levels to Decoder and Parser
With this change, decode times on GCC as measured by TestVP9Decode are
reduced by about 15%. Not a bad improvement for a few added lines :^)
2022-11-30 07:55:29 +01:00
Zaggy1024
3c68a6684e LibVideo: Don't crash when a decoder error is encountered while seeking
When errors are encountered by PlaybackManager, it attempts to switch
states to either Stopped or Corrupted. However, that causes it to set
the last presentation media time to the current playback time while the
last presentation time is unexpectedly negative because the seek never
ended.

Ending the seek before the state changes to Stopped or Corrupted
prevents this situation from happening.
2022-11-27 10:45:52 +01:00
Zaggy1024
f6830eaf73 LibVideo: Implement Matroska Cues for faster keyframe lookup
This implements the fastest seeking mode available for tracks with cues
using an array of cue points for each track. It approximates the index
based on the seeking timestamp and then finds the earliest cue point
before the timestamp. The approximation assumes that cues will be on
a regular interval, which I don't believe is always the case, but it
should at least be faster than iterating the whole set of cue points
each time.

Cues are stored per track, but most videos will only have cue points
for the video track(s) that are present. For now, this assumes that it
should only seek based on the cue points for the selected track. To
seek audio in a video file, we should copy the seeked iterator over to
the audio track's iterator after seeking is complete. The iterator will
then skip to the next audio block.
2022-11-25 23:28:39 +01:00
Zaggy1024
2a9fb8b439 LibVideo: Give Matroska duration an absolute value getter
Previously, the duration had to be multiplied by timestamp_scale and
converted to a Time object, now SegmentInformation::duration() does it
itself.
2022-11-25 23:28:39 +01:00
Zaggy1024
a58bf7c3d1 LibVideo: Calculate Block timestamps for Matroska according to spec
Tracks have a timestamp scale value that should be present which scales
each block's timestamp offset to allow video to be synced with audio.
They should also contain a CodecDelay element and may also contain a
TrackOffset that offsets the block timestamps.
2022-11-25 23:28:39 +01:00
Zaggy1024
fd3ffd88ce LibVideo: Add a fast seeking mode to seek only to keyframes
Now that we're able to find the nearest keyframe, we can have a fast
seeking mode that only seeks to keyframes, so that it doesn't have to
also decode inter frames until it reaches the timestamp.

The default is still accurate seeking, so that the entire seeking
implementation can be tested.
2022-11-25 23:28:39 +01:00
Zaggy1024
eef8867d9e LibVideo: Implement Matroska keyframe search for when there are no Cues
This just searches sequentially through each block in a SampleIterator
until it finds a block after the specified seek timestamp. Once it
finds one, it will try to set the input/output iterator to the most
recent keyframe. If the iterator's original position is closer to the
target, however, it leaves it at that original position, allowing
callers to continue decoding from that position until they reach the
target timestamp.
2022-11-25 23:28:39 +01:00
Zaggy1024
9040194d54 LibVideo: Make Matroska Block and Cluster timestamps absolute 2022-11-25 23:28:39 +01:00
Zaggy1024
5c2cede2c9 LibVideo: Implement accurate seeking to inter frames in PlaybackManager
This implements the PlaybackManager portion of seeking, so that it can
seek to any frame in the video by dropping all preceding frames until
it reaches the seek point.

MatroskaDemuxer currently will only seek to the start of the video.
That means that every seek has to drop all the frames until it comes
across the target timestamp.
2022-11-25 23:28:39 +01:00
Zaggy1024
9a9fe08449 LibVideo: Rewrite the video frame present function to be more readable
The PlaybackManager::update_presented_frame function was getting out of
hand and adding seeking was making it illegible. This rewrites it to be
(hopefully) quite a bit more readable, and adds a few comments to help
future readers of the code.

In addition, some helpful debugging prints were added that should help
debug any future issues with the player.
2022-11-25 23:28:39 +01:00
Zaggy1024
f31621b3f2 VideoPlayer/LibVideo: Implement the UI functionality for seeking
With these changes, the seek bar can be used, but only to seek to the
start of the file. Seeking to anywhere else in the file will cause an
error in the demuxer.

The timestamp label that was previously invisible now has its text set
according to either the playback or seek slider's position.
2022-11-25 23:28:39 +01:00
Zaggy1024
e216d1a65f LibVideo: Only print non-fatal playback errors when debug mode is on 2022-11-25 23:28:39 +01:00
Zaggy1024
393cfdd5c5 LibVideo: Read Matroska lazily so that large files can start quickly
The Demuxer class was changed to return errors for more functions so
that all of the underlying reading can be done lazily. Other than that,
the demuxer interface is unchanged, and only the underlying reader was
modified.

The MatroskaDocument class is no more, and MatroskaReader's getter
functions replace it. Every MatroskaReader getter beyond the Segment
element's position is parsed lazily from the file as needed. This means
that all getter functions can return DecoderErrors which must be
handled by callers.
2022-11-25 23:28:39 +01:00
Zaggy1024
f4c476b26f LibVideo: Make Matroska element parsing functions static
Making these functions static makes it easier to implement lazy-loading
since the parsing functions can now be called at any time.

The functions were reorganized because they were not defined in the
order they are called. However, instead of moving every function to
that order, I've declared some but defined them further into the file,
which allows the next commit's diff to be more readable.
2022-11-25 23:28:39 +01:00
Zaggy1024
be9de58932 LibVideo: Parse Matroska from ReadonlyBytes and keep the start position
Keeping the entire Matroska stream available is a prerequisite to being
able to stream from it and seek to cue points.
2022-11-25 23:28:39 +01:00
Zaggy1024
2dfd236dcd LibVideo: Propagate decoder errors in the Matroska Reader
Matroska::Reader functions now return DecoderErrorOr instead of values
being declared Optional. Useful errors can be handled by the users of
the parser, similarly to the VP9 decoder. A lot of the error checking
in the reader is a lot cleaner thanks to this change, since all reads
can be range checked in Streamer::read_octet() now.

Most functions for the Streamer class are now also out-of-line in
Reader.cpp now instead of residing in the header.
2022-11-25 23:28:39 +01:00
Zaggy1024
9cf7e8c5aa LibVideo: Reorganize demuxer file hierarchy and rename Matroska files
As new demuxers are added, this will get quite full of files, so it'll
be good to have a separate folder for these.

To avoid too many chained namespaces, the Containers subdirectory is
not also a namespace, but the Matroska folder is for the sake of
separating the multiple classes for parsed information entering the
Video namespace.
2022-11-25 23:28:39 +01:00
Zaggy1024
edec6bdc32 LibVideo: Make all PlaybackManager Timer::start calls set an interval
Timers keep their previously set interval even for single-shot mode.
We want all timers to fire immediately if they don't have a delay set
in the start() call.
2022-11-25 23:28:39 +01:00
Zaggy1024
7514e49c17 LibVideo: Make all VP9 block intermediates stack-allocated arrays
This has two benefits:
- I observed a ~34% decrease in decoding time running TestVP9Decode.
- Removing all of these silly Vector fields helps simplify the code
  relationships between all the functions in Decoder.cpp. It'll also be
  much easier to make these static with template specializations, if
  that turns out to be worthy performance improvement.
2022-11-25 02:44:18 +03:30
Zaggy1024
87aed17a46 VideoPlayer: Make PlaybackManager use OwnPtr
VideoPlayerWidget was keeping a reference to PlaybackManager when
changing files, so the old and new managers would both send frames to
be presented at the same time, causing it to flicker back and forth
between the two videos. However, PlaybackManager no longer relies on
event bubbling to pass events to its parent. By changing it to send
events directly to an Object, it can avoid being ref counted, so that
it will get destroyed with its containing object and stop sending
events.
2022-11-14 10:05:56 +00:00
Zaggy1024
9dc622475e LibVideo: Rename parse_tree_new to parse_tree in VP9/TreeParser.cpp
It is now the only function used to parse the binary trees in the VP9
decoder.
2022-11-12 10:17:27 -07:00
Zaggy1024
907816e629 LibVideo: Create TokensContext struct for token parsing parameters
With the addition of this struct, both the bool to determine if coefs
should be parsed and the token parse itself can take specific
parameters.

This is the last step in parameterizing all the tree parsing, so the
old functions in TreeParser are now unused. This patch is very
satisfying :^)

There's still more work to be done to clean up how the parameters are
passed from Parser, but that's work for another day.
2022-11-12 10:17:27 -07:00
Zaggy1024
e906bcc696 LibVideo: Parameterize all tree parsing for motion vectors in VP9 2022-11-12 10:17:27 -07:00
Zaggy1024
84f1aed40a LibVideo: Parameterize parsing single reference frame selection in VP9 2022-11-12 10:17:27 -07:00
Zaggy1024
37fab851f1 LibVideo: Parameterize parsing compound references in the VP9 decoder 2022-11-12 10:17:27 -07:00
Zaggy1024
dd18c42643 LibVideo: Parameterize compound mode parsing in the VP9 decoder 2022-11-12 10:17:27 -07:00
Zaggy1024
372a4ea8c1 LibVideo: Parameterize parsing if a block is inter predicted in VP9 2022-11-12 10:17:27 -07:00
Zaggy1024
93caa1e19d LibVideo: Parameterize TXSize parsing for the VP9 decoder 2022-11-12 10:17:27 -07:00
Zaggy1024
cc735a7001 LibVideo: Parameterize coefficient skip parsing for VP9 2022-11-12 10:17:27 -07:00
Zaggy1024
10ba956066 LibVideo: Parameterize segment ID parsing for the VP9 decoder 2022-11-12 10:17:27 -07:00
Zaggy1024
568e2fc1f2 LibVideo: Parameterize interpolation filter parsing for the VP9 decoder 2022-11-12 10:17:27 -07:00
Zaggy1024
cbb8a3f0f4 LibVideo: Parameterize inter mode parsing in the VP9 decoder 2022-11-12 10:17:27 -07:00
Zaggy1024
540ef22b95 LibVideo: Parameterize UV mode parsing in the VP9 decoder 2022-11-12 10:17:27 -07:00
Zaggy1024
858915ab3a LibVideo: Parameterize intra prediction mode parsing for VP9 2022-11-12 10:17:27 -07:00
Zaggy1024
1b66aa3cad LibVideo: Parameterize parsing the default UV prediction mode for VP9 2022-11-12 10:17:27 -07:00
Zaggy1024
c6ecad63d0 LibVideo: Parameterize parsing of the default VP9 intra mode tree 2022-11-12 10:17:27 -07:00
Zaggy1024
fce7639c90 LibVideo: Put motion vector or reference frame pairs in a struct
Since these two types are often passed around as a pair, it's easier to
handle them with a simple pair struct, at least for now. Once things
are fully being passed around as parameters wherever possible, it may
be good to change this type for something more generalized.
2022-11-12 10:17:27 -07:00
Zaggy1024
6192a33e79 LibVideo: Move parsing of Partition to its own TreeParser function
This adds a tree-parsing function that can be called statically from
specific trees' implementations in TreeParser, of which Partition is
the first. This way, all calls to tree parses will take the context
they need to be able to select a tree and probabilities, which will
allow removal of the state dependence in TreeParser on fields from
itself and Parser.
2022-11-12 10:17:27 -07:00
Zaggy1024
69e6feaf32 LibVideo: Add const getters to VP9/ProbabilityTables.h 2022-11-12 10:17:27 -07:00
Zaggy1024
17e1b205a4 LibVideo: Use the BlockSubsize enum where appropriate in the VP9 parser 2022-11-12 10:17:27 -07:00
Zaggy1024
981997c039 LibVideo: Combine VP9's Intra- and InterMode enums into PredictionMode
The two different mode sets are stored in single fields, and the
underlying values didn't overlap, so there was no reason to keep them
separate.

The enum is now an enum class as well, to enforce that almost all uses
of the enum are named. The only case where underlying values are used
is in lookup tables, but it may be worth abstracting that as well to
make array bounds more clear.
2022-11-12 10:17:27 -07:00
Zaggy1024
1c6d0a9777 LibVideo: Use Gfx::Size for VP9 frame sizes
Frame sizes will now be represented by Gfx::Size instead of storing
width and height separately.
2022-11-12 10:17:27 -07:00
Zaggy1024
40b0bb0914 LibVideo: Change all Span<u8 const> to ReadonlyBytes 2022-11-12 10:17:27 -07:00
Zaggy1024
72ed286e16 LibVideo: Allow the VP9 decoder to queue multiple frames
Frames will now be queued for retrieval by the user of the decoder.
When the end of the current queue is reached, a DecoderError of
category NeedsMoreInput will be emitted, allowing the caller to react
by displaying what was previously retrieved for sending more samples.
2022-11-12 10:17:27 -07:00
Zaggy1024
993385f18d LibVideo: Rename VP9's ReferenceFrame enum to ReferenceFrameType 2022-11-12 10:17:27 -07:00
Zaggy1024
6b392cef9c LibVideo: Treat BT.601/709/2020 input transfer characteristics as sRGB
I've realized that it probably makes more sense to change the input
transfer characteristics to treat these as sRGB since color conversion
in linear converted from BT.709 doesn't really make sense. If content
creation applications expect media players to display BT.709 without
conversions, this means they expect applications to treat it as sRGB,
since that's what most displays use. That most likely also means they
process it as sRGB internally, meaning we should do the same for our
color primaries conversion.
2022-11-11 11:34:03 +01:00
Zaggy1024
6f28c8deb0 LibVideo: Remove control codes from DecoderError location information 2022-11-10 12:32:55 +03:30
Zaggy1024
18a6a1dd10 LibVideo: Handle corrupted video errors without spamming dialogs
No longer will the video player explode with error dialogs that then
lock the user out of closing them.

To avoid issues where the playback state becomes invalid when an error
occurs, I've made all decoder errors pass through the frame queue.
This way, when a video is corrupted, there should be no chance that the
playback state becomes invalid due to setting the state to Corrupted
in the event handler while a presentation event is still pending.
Or at least I think that was what caused some issues I was seeing :^)

This system should be a lot more robust if any future errors need to be
handled.
2022-11-10 12:32:55 +03:30