2011-05-08 19:12:35 +02:00
|
|
|
Design: Playback and Render Control
|
|
|
|
|
===================================
|
|
|
|
|
:Author: Ichthyostega
|
|
|
|
|
:Date: 5/2011
|
|
|
|
|
|
|
|
|
|
//MENU: label Player subsystem
|
|
|
|
|
|
|
|
|
|
**************************************************************************************
|
2022-08-28 23:36:27 +02:00
|
|
|
This part of the architecture is concerned with how to initiate, coordinate and control
|
2011-05-08 19:12:35 +02:00
|
|
|
the calculation processes necessary to generate visible / audible data from our source
|
|
|
|
|
media. This design is _not so much_ concerned with the actual calculations; indeed it
|
2013-01-06 16:16:58 +01:00
|
|
|
takes a ``birds eye view'', treating the actual render engine mostly just like an
|
2011-05-08 19:12:35 +02:00
|
|
|
opaque entity providing some service.
|
|
|
|
|
**************************************************************************************
|
|
|
|
|
|
|
|
|
|
Collecting initial drafts
|
|
|
|
|
-------------------------
|
|
|
|
|
|
2013-01-06 16:16:58 +01:00
|
|
|
At the start of 2011, several design sketches emerged as an offspring of other
|
|
|
|
|
discussions and brainstorming sessions.
|
2011-05-08 19:12:35 +02:00
|
|
|
|
|
|
|
|
* the link:/documentation/devel/rfc_pending/EngineInterfaceOverview.html[Engine Interface draft]
|
|
|
|
|
contains some fundamental terms and definitions.
|
2013-01-06 16:16:58 +01:00
|
|
|
* discussions regarding time values and timecode handling shed some light on the requirements
|
2011-05-08 19:12:35 +02:00
|
|
|
to be fulfilled by a player subsystem
|
|
|
|
|
|
|
|
|
|
- link:http://article.gmane.org/gmane.comp.video.lumiera.general/2116[Timecode Widget and Framerates]
|
|
|
|
|
- link:http://article.gmane.org/gmane.comp.video.lumiera.general/2109[Time, Time-spans, Quatisation and Timecode]
|
2018-10-26 17:47:18 +02:00
|
|
|
- link:{l}/wiki/renderengine.html#TimeQuant[Definition of Time entities]
|
2011-05-10 02:49:31 +02:00
|
|
|
from the implementation notes in the TiddlyWiki
|
2011-05-08 19:12:35 +02:00
|
|
|
|
|
|
|
|
|
2013-01-06 16:16:58 +01:00
|
|
|
Reasoning Behind the Player Subsystem's Structure
|
2011-05-10 02:49:31 +02:00
|
|
|
------------------------------------------------
|
2011-05-08 19:12:35 +02:00
|
|
|
|
2013-01-06 16:16:58 +01:00
|
|
|
The name ``Player'' might seem surprising at first.
|
2011-05-08 19:12:35 +02:00
|
|
|
The full, complete and precise name would be something along
|
2011-05-10 02:49:31 +02:00
|
|
|
the lines of ``_render- and playback-process coordination subsystem_''.
|
2013-01-06 16:16:58 +01:00
|
|
|
However we need to shorten that into a single word. The more obvious
|
|
|
|
|
abbreviation (assuming importance of words to be the selection criteria) would be
|
|
|
|
|
_Render_, but that would be strikingly misleading, because everyone would take
|
|
|
|
|
that to refer to the render engine. Thus, we are left with _Player_. A second
|
|
|
|
|
consideration highlights similarities to the structure of a
|
|
|
|
|
typical software player -- the term we selected turns out to be suitably
|
|
|
|
|
aligned to the actual nature of that subsystem.
|
2011-05-10 02:49:31 +02:00
|
|
|
|
|
|
|
|
Influences and Requirements
|
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
|
|
|
|
|
In accordance with the spirit of modern software development, the analysis
|
2013-01-06 16:16:58 +01:00
|
|
|
starts by determining the _Service_ that is provided by such a
|
|
|
|
|
player. Examination of the Use Cases determines the fundamental forces
|
2011-05-10 02:49:31 +02:00
|
|
|
to be _multiplicity_, combined with _differentiation in detail_, all under
|
|
|
|
|
the government of _time-bound delivery_, combined with _live reconfiguration_.
|
|
|
|
|
|
2013-01-06 16:16:58 +01:00
|
|
|
The basic service turns out to be *performing of a preconfigured object model*.
|
2011-05-10 02:49:31 +02:00
|
|
|
This performance is *time based*. Multiple usage instances of this service can
|
|
|
|
|
be expected to coexist, each of which can be broken down into a set of *elementary
|
2011-05-11 21:06:25 +02:00
|
|
|
streams to be delivered in sync*. The parameters of delivery can be *reconfigured
|
2011-05-10 02:49:31 +02:00
|
|
|
on-the-fly*.
|
|
|
|
|
|
2013-01-06 16:16:58 +01:00
|
|
|
Modes of Operation
|
2011-05-10 02:49:31 +02:00
|
|
|
^^^^^^^^^^^^^^^^^^
|
2013-01-06 16:16:58 +01:00
|
|
|
Delivery can be either _free-wheeling_, so as to cover a predefined time interval
|
2011-05-10 02:49:31 +02:00
|
|
|
with fixed quality calculations (final render), and it can be _throttled_ for using
|
|
|
|
|
excess computation power (background rendering). Or -- alternatively -- delivery can
|
|
|
|
|
be _time-bound_ (for classical playback), following the projection of wall clock time
|
|
|
|
|
onto a predefined timeline interval (the so called ``playhead'' or ``playback cursor''
|
|
|
|
|
proceeding along a timeline).
|
|
|
|
|
|
|
|
|
|
Reconfiguration
|
|
|
|
|
^^^^^^^^^^^^^^^
|
2011-05-22 05:45:59 +02:00
|
|
|
Some of these operation modes need to be prepared to encounter an unpredictable live
|
2013-01-06 16:16:58 +01:00
|
|
|
reconfiguration driven by user interactions:
|
2011-05-10 02:49:31 +02:00
|
|
|
|
|
|
|
|
- any part of background rendering can be invalidated and restarted, while other parts
|
2013-01-06 16:16:58 +01:00
|
|
|
should be re-integrated, possibly with a re-adjusted position
|
|
|
|
|
- playback, which evolves in a linear manner, can be in one of any of these
|
|
|
|
|
states at any particular time :
|
2011-05-10 02:49:31 +02:00
|
|
|
|
|
|
|
|
* paused
|
|
|
|
|
* reversed in direction
|
2013-01-06 16:16:58 +01:00
|
|
|
* playback speed re-adjusted
|
2011-05-10 02:49:31 +02:00
|
|
|
|
2013-01-06 16:16:58 +01:00
|
|
|
- playback can be looped, with _unlimited_ adjustments of the loop boundaries at
|
|
|
|
|
any time.
|
2011-05-10 02:49:31 +02:00
|
|
|
|
|
|
|
|
|
2011-05-08 19:12:35 +02:00
|
|
|
|
2011-05-11 03:08:27 +02:00
|
|
|
Conclusions for the Design
|
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~
|
2011-05-08 19:12:35 +02:00
|
|
|
|
2013-01-06 16:16:58 +01:00
|
|
|
Based on these observations, the following design would appear to be pretty much
|
|
|
|
|
obvious:
|
2011-05-08 19:12:35 +02:00
|
|
|
|
2013-01-06 16:16:58 +01:00
|
|
|
The overall player subsystem can be described as ``play/render-this''-service.
|
|
|
|
|
Given a suitable (high-level) object, the player has the ability to ``perform''
|
|
|
|
|
(play or render) the object.
|
2011-05-08 19:12:35 +02:00
|
|
|
|
2013-01-06 16:16:58 +01:00
|
|
|
- the standard operation is _playing a timeline_.
|
|
|
|
|
- it is conceivable that playing a selection of other objects would be
|
|
|
|
|
permitted, for example, directly playing a clip or even a media asset. In
|
|
|
|
|
these cases, it is the player's job to prepare the scaffolding that
|
|
|
|
|
is required on the fly.
|
2011-05-08 19:12:35 +02:00
|
|
|
|
2011-05-11 03:08:27 +02:00
|
|
|
Yet each such performance of an object is a _stateful instance_, a player application:
|
2013-01-06 16:16:58 +01:00
|
|
|
on application of the player service, the client obtains a front-end handle, a *play-controller*,
|
|
|
|
|
which is a _state machine_. This provides states and transitions such as 'play', 'pause', 'ffwd',
|
|
|
|
|
'rew', 'goto', 'step', 'scrub' and similar. Moreover, it maintains (or connects to) a distinct
|
|
|
|
|
playback location, and it can be hooked up to a play-control GUI widget
|
|
|
|
|
(or something simpler in the case of a render process, which is free wheeling).
|
2011-05-08 19:12:35 +02:00
|
|
|
|
2013-01-06 16:16:58 +01:00
|
|
|
Each play-controller, in turn, is then associated with several *play/render-processes*,
|
2011-05-11 03:08:27 +02:00
|
|
|
one for each independent media stream (channel) to be produced. Of course this
|
2011-05-22 05:45:59 +02:00
|
|
|
isn't an operating system process; rather, each such process is a compound of entries
|
2013-01-06 16:16:58 +01:00
|
|
|
in a registration table, which serves the purpose of tying several other services together,
|
2011-05-11 03:08:27 +02:00
|
|
|
which we initiate and use in order to make that render process happen.
|
2013-01-06 16:16:58 +01:00
|
|
|
Most notably, we'll use the services of the actual engine which provides us with
|
|
|
|
|
a kind of a *calculation stream service*: the ability to deliver a sequence of
|
|
|
|
|
calculated data frames in a timely fashion.
|
2011-05-08 19:12:35 +02:00
|
|
|
|
2011-05-11 03:08:27 +02:00
|
|
|
When a client requests such an instance of the player service, we build up these
|
|
|
|
|
parts providing that service, which cascades down to the individual elements.
|
2013-01-06 16:16:58 +01:00
|
|
|
At that point, we need to pull and combine two kinds of information:
|
2011-05-11 03:08:27 +02:00
|
|
|
|
|
|
|
|
- the ``what'' to render: this information stems from the session/model.
|
|
|
|
|
- the ``how'' to render: this information is guided by the derived output configuration.
|
|
|
|
|
|
2013-01-06 16:16:58 +01:00
|
|
|
Viewer and Output Connection
|
2011-05-11 03:08:27 +02:00
|
|
|
^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
2013-01-06 16:16:58 +01:00
|
|
|
Creating a player instance binds three partners together: a _timeline_, a _viewer_
|
|
|
|
|
and _the engine_. While the timeline provides the contents to play, the _viewer connection_
|
|
|
|
|
is crucial for working out the actual output sink(s) and, hence, the output format to use.
|
|
|
|
|
Thus, a viewer connection is a prerequisite in order to create a player instance.
|
2011-05-11 03:08:27 +02:00
|
|
|
|
2013-01-06 16:16:58 +01:00
|
|
|
Viewer connections exist as associations in the session/model -- which are entities separate
|
2011-05-11 03:08:27 +02:00
|
|
|
from the player. Usually, a timeline has (at least) one viewer connection. But in case
|
|
|
|
|
such a connection is (still) missing, building a player instance recurs to the session
|
|
|
|
|
to get a suitable viewer _allocated_. The viewer connection can't be broken during the
|
|
|
|
|
lifetime of that player instance (or putting it the other way: breaking that viewer
|
|
|
|
|
connection, e.g. by forcing a different connection or by shutting down the viewer,
|
2013-01-06 16:16:58 +01:00
|
|
|
immediately terminates the player.) This detaching works synchronously, i.e. it
|
|
|
|
|
blocks until all the allocated _output slots_ can be released.
|
2011-05-11 03:08:27 +02:00
|
|
|
|
|
|
|
|
Live switching
|
|
|
|
|
^^^^^^^^^^^^^^
|
|
|
|
|
While the viewer connection can be treated as fixed during the lifespan of a player
|
2013-01-06 16:16:58 +01:00
|
|
|
instance, several life switching and reconfiguration operations might happen at any time:
|
|
|
|
|
the _model port_ (the place where data is retrieved from calculation), the output characteristics
|
2011-05-11 03:08:27 +02:00
|
|
|
(framerate, direction) and the delivery goals (playback position, loop playing, scrubbing)
|
|
|
|
|
all may be changed during playback -- we need a way for the player to ``cancel'' and
|
2018-11-15 21:13:52 +01:00
|
|
|
reconfigure the vault layer services.
|
2011-05-11 03:08:27 +02:00
|
|
|
|
|
|
|
|
Frame quantisation
|
|
|
|
|
^^^^^^^^^^^^^^^^^^
|
2013-01-04 01:45:47 +01:00
|
|
|
link:../TimeQuant.html[Quantisation] is a kind of rounding; like any kind of rounding, quantisation is
|
2011-05-11 03:08:27 +02:00
|
|
|
a dangerous operation because it kills information content.
|
2011-05-08 19:12:35 +02:00
|
|
|
|
2013-01-06 16:16:58 +01:00
|
|
|
Thus, there are three fundamental guidelines when it comes to rounding:
|
2011-05-10 02:49:31 +02:00
|
|
|
|
|
|
|
|
. don't do it
|
|
|
|
|
. do it at most once
|
|
|
|
|
. do it as late as possible
|
2011-05-08 19:12:35 +02:00
|
|
|
|
|
|
|
|
These may guide the process of finding the right place for the Quantiser(s) to
|
|
|
|
|
apply. We need some information flows to be joined in order to be able to do
|
|
|
|
|
the quantisation, which leaves us with just a few possible junction points
|
2018-11-15 21:13:52 +01:00
|
|
|
where to place quantisation: the Vault, the GUI, the player and the session.
|
2011-05-08 19:12:35 +02:00
|
|
|
|
2018-11-15 21:13:52 +01:00
|
|
|
- putting it into the vault layer seems to be the most reasonable at first sight:
|
2013-01-06 16:16:58 +01:00
|
|
|
we can ``do away'' with nasty things soon, especially if they are technicalities,
|
2011-05-11 03:08:27 +02:00
|
|
|
``get a clean state soon'' -- and hasn't frame quantisation something to do
|
2018-11-16 22:38:29 +01:00
|
|
|
with media data, which is handled in the vault?
|
2011-05-11 03:08:27 +02:00
|
|
|
+
|
|
|
|
|
Well, actually, all of those are pitfalls to trap the unwary. About
|
2013-01-06 16:16:58 +01:00
|
|
|
cleanliness, well, sigh! Doing rounding soon will leave us with a huge
|
|
|
|
|
amount of degraded information flows throughout the whole system; as a
|
|
|
|
|
consequence, the general rule is to do it as late as possible. Uncrippled
|
|
|
|
|
information is an enablement. And last but not least: the frame quantisation is connected
|
2018-11-15 21:13:52 +01:00
|
|
|
to the _output_ format -- and the vault layer is likely within the whole
|
2011-05-22 05:45:59 +02:00
|
|
|
application the subsystem most remote and unaware of output requirements.
|
2011-05-11 03:08:27 +02:00
|
|
|
|
|
|
|
|
- rounding/quantising in the GUI is extremely common within media applications;
|
2013-01-06 16:16:58 +01:00
|
|
|
unfortunately there does not appear to be a single rational argument in
|
|
|
|
|
support of this habit. Most of all, it is a violation of the subsidiarity
|
|
|
|
|
principle.
|
2011-05-08 19:12:35 +02:00
|
|
|
|
|
|
|
|
Which leaves us with the player and the session. Both positions could
|
2011-05-11 03:08:27 +02:00
|
|
|
arguably be supported. Here, a more careful consideration shows, that
|
|
|
|
|
the ``act of frame rounding'' can be decomposed: into the _act of quantisation_
|
2013-01-06 16:16:58 +01:00
|
|
|
and the _frame grid_. Basically it is the session which has the ability
|
2011-05-22 05:45:59 +02:00
|
|
|
to form the *frame grid*, but it is lacking crucial information about
|
2011-05-11 03:08:27 +02:00
|
|
|
the output. Only when connecting both -- which is the essence of the
|
|
|
|
|
player -- frame quantisation can actually be performed. Thus, the
|
|
|
|
|
player is the natural location to perform that quantisation operation.
|
2011-05-08 19:12:35 +02:00
|
|
|
|