1
Fork 0
mirror of https://github.com/RGBCube/serenity synced 2025-05-20 14:25:08 +00:00
Commit graph

300 commits

Author SHA1 Message Date
Zaggy1024
b966f9d811 LibVideo/VP9: Move the transform mode field from Parser to FrameContext 2022-11-30 08:28:30 +01:00
Zaggy1024
396972bb69 LibVideo/VP9: Retain adjacent block contexts storage between frames
Re-allocating the storage is unnecessary, since the size will rarely
change during playback.
2022-11-30 08:28:30 +01:00
Zaggy1024
ea7a6f343b LibVideo/VP9: Select and read motion vectors without fields in Parser
Candidate vector selections are only used to calculate the new vectors
for the current block, so we only need to keep those for the duration
of the inter_block_mode_info() call.

Candidate vectors are now stored in BlockMotionVectorCandidates, which
contains the fields necessary to choose the vector to use to sample
from the selected reference frame.

Most functions related to motion vectors were renamed to more verbose
but meaningful names.
2022-11-30 08:28:30 +01:00
Zaggy1024
368687a74f LibVideo/VP9: Store tile counts in FrameContext
The log2 of tile counts in the horizontal and vertical dimensions are
now stored in the FrameContext struct to be kept only as long as they
are needed.
2022-11-30 08:28:30 +01:00
Zaggy1024
6533c5f6a8 LibVideo/VP9: Move more block fields into the BlockContext struct
This includes the segment IDs, transform block sizes, prediction modes,
sub-block counts, interpolation filters and sub-block motion vectors.
2022-11-30 08:28:30 +01:00
Zaggy1024
f4e835635f LibVideo/VP9: Move quantizer indices into FrameContext
This also renames (most?) of the related quantizer functions and
variables to make more sense. I haven't determined what AC/DC stands
for here, but it may be just an arbitrary naming scheme for the first
and subsequent coefficients used to quantize the residuals for a block.
2022-11-30 08:28:30 +01:00
Zaggy1024
0df5c1f32f LibVideo/VP9: Move loop filter parameters to FrameContext 2022-11-30 08:28:30 +01:00
Zaggy1024
90f16c78fa LibVideo/VP9: Move fields set in uncompressed_header() to FrameContext 2022-11-30 08:28:30 +01:00
Zaggy1024
40bc987fe3 LibVideo/VP9: Store color config in the frame context
The color config is reused for most inter predicted frames, so we use a
struct ColorConfig to store the config from intra frames, and put it in
a field in Parser to copy from when an inter frame without color config
is encountered.
2022-11-30 08:28:30 +01:00
Zaggy1024
9f573264ea LibVideo/VP9: Add a FIXME to keep render_and_frame_size_different
The flag should be used to determine whether the pixel aspect ratio
should be updated when frame/render sizes change in the bitstream.
2022-11-30 08:28:30 +01:00
Zaggy1024
3259c99cab LibVideo/VP9: Choose whether/how to show new frames using an enum
There are three mutually exclusive frame-showing states:
- Show no new frame, only store the frame as a reference.
- Show a newly decoded frame.
- Show frame from the reference frame store.
Since they are mutually exclusive, using an enum rather than two bools
makes more sense.
2022-11-30 08:28:30 +01:00
Zaggy1024
befcd479ae LibVideo/VP9: Add Frame, Tile and Block context structs
These are used to pass context needed for decoding, with mutability
scoped only to the sections that the function receiving the contexts
needs to modify. This allows lifetimes of data to be more explicit
rather than being stored in fields, as well as preventing tile threads
from modifying outside their allowed bounds.
2022-11-30 08:28:30 +01:00
Zaggy1024
448a8b8efb LibVideo/VP9: Create Vector2DView to limit writable ranges of contexts 2022-11-30 08:28:30 +01:00
Zaggy1024
9da432f4d6 LibVideo/VP9: Remove m_eob_total field from parser
The field was only used once to track whether residual tokens were
present in the block. Parser::tokens() now returns a bool indicating
whether they were present.
2022-11-30 08:28:30 +01:00
Zaggy1024
10d207959d LibVideo/VP9: Remove m_mi_row and col fields from the parser
These are now passed as parameters to each function that uses them.
These will later be moved to a struct to further reduce the amount of
parameters that get passed around.

Above and left per-frame block contexts are now also parameters passed
to the functions that use them instead of being retrieved when needed
from a field. This will allow them to be more easily moved to a tile-
specific context later.
2022-11-30 08:28:30 +01:00
Zaggy1024
4a4aa697d9 LibVideo/VP9: Use a struct for block context to keep between frames
There are three fields that we need to store from FrameBlockContext to
keep between frames, which are used to parse for those same fields for
the next frame.
2022-11-30 08:28:30 +01:00
Zaggy1024
5275a1101e LibVideo/VP9: Remove dump_frame_info() function from Decoder
The function serves no purpose now, any debug information we want to
pull from the decoder should be instead accessed by some other yet to
be created interface.
2022-11-30 08:28:30 +01:00
Zaggy1024
0638c5d2b8 LibVideo/VP9: Use a class to store 2D context information 2022-11-30 08:28:30 +01:00
Zaggy1024
44413c31a9 LibVideo/VP9: Store data used between decode_block calls in a struct
All state that needed to persist between calls to decode_block was
previously stored in plain Vector fields. This moves them into a struct
which sets a more explicit lifetime on that data. It may be possible to
store this data on the stack of a function with the appropriate
lifetime now that it is split into its own struct.
2022-11-30 08:28:30 +01:00
Zaggy1024
9b6ab1d4e5 LibVideo/VP9: Change fields within decode_partition() to variables 2022-11-30 08:28:30 +01:00
Zaggy1024
e379223633 LibVideo/VP9: Don't store the default_intra_mode in a field
The default intra prediction mode was only used to set the sub-block
modes and the y prediction mode. Instead of storing it in a field, with
the sub modes are stored in an Array, we can just pull the last element
to set the y mode.
2022-11-30 08:28:30 +01:00
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