1. 23 Mar, 2020 40 commits
    • Romain Vimont's avatar
      opengl: insert shader headers at compile time · 7d385290
      Romain Vimont authored
      The version and precision header strings are different for OpenGL and
      OpenGL ES.
      
      Insert them directly into the shader string literal, instead of
      initializing renderer fields and inserting them at runtime.
      7d385290
    • Romain Vimont's avatar
      opengl: do not store a copy of fmt in renderer · 37304221
      Romain Vimont authored
      The renderer format is, by definition, the one of its sampler. There is
      no need to copy it.
      37304221
    • Romain Vimont's avatar
      opengl: use TransformMatrix to apply OpenGL vflip · 0686e998
      Romain Vimont authored
      Uploading a picture_t to OpenGL flips it vertically.
      
      To display the video in the correct orientation, the renderer reversed
      the transformation: each vertex received as attribute texture
      coordinates (x, 1-y) instead of (x, y), in order to flip the image
      vertically.
      
      This caused several problems.
      
      Firstly, the renderer must be independent of the input picture storage.
      Otherwise, when it will receive an input in the correct orientation, it
      will wrongly apply a vertical flip.
      
      Secondly, since the vflip was applied on the input coordinates, it
      occurred before the orientation transform:
      
          OrientationMatrix * VFlipMatrix * input_coords  (semantically)
      
      whereas the correct transformation is:
      
          VFlipMatrix * OrientationMatrix * input_coords
      
      (for reasons explained in e329c4bb).
      
      Since matrix multiplication is not commutative, it resulted in a
      wrong orientation in some cases (for example if OrientationMatrix
      contains a rotation by 90°).
      
      (In fact, in pratice, this case still worked, because the initialization
      of OrientationMatrix was also wrong, see the two previous commits).
      
      To fix all these problems, initialize the texture coordinates in the
      normal orientation in the renderer, and apply the vertical flip using
      the TransformationMatrix in the sampler.
      
      This also allows to simplify the Android interop, which can just provide
      its own transform matrix without compensating for the vertical flip
      that was applied in the renderer.
      0686e998
    • Romain Vimont's avatar
      opengl: rename "prepare_shader" callback to "load" · a0c3b438
      Romain Vimont authored
      The purpose of this callback is to load sampler data (bind textures,
      load uniforms, etc.) to be used for the OpenGL draw call.
      
      The name "load" also allows to possibly add an "unload" function later
      (to reset bindings).
      a0c3b438
    • Romain Vimont's avatar
      opengl: group sampler callbacks into struct ops · 62a077dd
      Romain Vimont authored
      This makes explicit that these functions are set by the sampler
      implementation and must be called by the user of sampler.
      62a077dd
    • Romain Vimont's avatar
      opengl: make FetchLocations() infaillible · dcf1d6c1
      Romain Vimont authored
      If GetUniformLocation() returns -1, then this is an implementation
      error.
      
      Assert instead of reporting the error to the caller.
      dcf1d6c1
    • Romain Vimont's avatar
      opengl: move "dump shaders" flag to renderer · c7560080
      Romain Vimont authored
      Only the renderer dumps its shaders depending on the verbose level.
      c7560080
    • Romain Vimont's avatar
      opengl: merge DrawWithShaders() into _Draw() · 7e42ee40
      Romain Vimont authored
      The function vlc_gl_renderer_Draw() (almost) just called
      DrawWithShaders(). There is no need for a separate function.
      7e42ee40
    • Romain Vimont's avatar
      opengl: do not pass the picture_t to the renderer · e2b56c3b
      Romain Vimont authored
      The renderer is expected to be independant of the input picture format.
      Instead, update the sampler directly.
      e2b56c3b
    • Romain Vimont's avatar
      opengl: remove all interop usages from renderer · a76289f5
      Romain Vimont authored
      Remove the remaining usage of interop from renderer.
      
      Now, the renderer only need to use the sampler.
      a76289f5
    • Romain Vimont's avatar
      opengl: move sampler ownership to vgl · 4e580ac1
      Romain Vimont authored
      The sampler were owned by the renderer.
      
      Move it to vgl, so that the renderer never have to handle an interop
      instance directly.
      4e580ac1
    • Romain Vimont's avatar
      opengl: update pictures from sampler · 876b4634
      Romain Vimont authored
      The renderer should not know the interop, so it may not be responsible
      to upload the textures.
      
      Move the pictures update to sampler.
      876b4634
    • Romain Vimont's avatar
      opengl: move orientation matrix init to sampler · 09732d34
      Romain Vimont authored
      The orentation matrix is managed by the sampler. Move its initialization
      to opengl_fragment_shader_init() (called by the sampler).
      09732d34
    • Romain Vimont's avatar
      opengl: move sampler initialization to constructor · 50b83c70
      Romain Vimont authored
      Move opengl_fragment_shader_init() call from renderer to sampler.
      50b83c70
    • Romain Vimont's avatar
      opengl: generate the extensions from the sampler · bb071f4f
      Romain Vimont authored
      The sampler handles the input pictures, so it is also responsible for
      generating the necessary GLSL extensions code (if any).
      bb071f4f
    • Romain Vimont's avatar
      opengl: store fragment shader in sampler · 5df7f113
      Romain Vimont authored
      The function opengl_fragment_shader_init() both initializes the
      and creates the fragment shader.
      
      To be able to move its initialization outside the renderer, store it in
      the sampler instead of returning it. This will also allow to provide the
      "extensions" part of the fragment shader as a separate string.
      5df7f113
    • Romain Vimont's avatar
      opengl: only use sampler from fragment_shaders.c · 81178eb9
      Romain Vimont authored
      The renderer instance is not needed anymore.
      81178eb9
    • Romain Vimont's avatar
      opengl: remove interop reference from renderer · 54c72556
      Romain Vimont authored
      Remove the (weak) reference to the interop from the renderer structure.
      
      The interop is still accessed explicitly from the renderer via the
      sampler structure for now.
      54c72556
    • Romain Vimont's avatar
      opengl: expose functions to call sampler callbacks · 505f734e
      Romain Vimont authored
      The fact that the sampler use internal function pointers (instead of
      if-blocks for example) is an internal detail.
      505f734e
    • Romain Vimont's avatar
      opengl: simplify pf_prepare_shader() · 3baa75fc
      Romain Vimont authored
      Remove tex_width and tex_height parameters, as they are either unused or
      accessible from the sampler itself.
      3baa75fc
    • Romain Vimont's avatar
      opengl: remove alpha parameter from prepare_shader · d08fe4c4
      Romain Vimont authored
      The alpha value was used to render subpictures, which are now drawn by
      the subpictures renderer using its own fragment shader.
      d08fe4c4
    • Romain Vimont's avatar
      opengl: load uniforms from sampler · 82d5afb3
      Romain Vimont authored
      Load uniforms related to sampler from sampler->pf_prepare_shader.
      82d5afb3
    • Romain Vimont's avatar
      opengl: fetch locations from sampler · 0015c6e9
      Romain Vimont authored
      Fetch locations related to sampler from sampler->pf_fetch_locations.
      0015c6e9
    • Romain Vimont's avatar
      opengl: move callbacks to sampler · 33f58950
      Romain Vimont authored
      The sampler is responsible to fetch its location and initialize its
      textures and uniforms.
      33f58950
    • Romain Vimont's avatar
      opengl: define identity matrices in gl_util.h · 75e72022
      Romain Vimont authored
      This will allow to use them from several files.
      75e72022
    • Romain Vimont's avatar
      opengl: extract sampler creation and destruction · b4fc0528
      Romain Vimont authored
      Extract sampler creation and destruction to separate functions.
      b4fc0528
    • Romain Vimont's avatar
      opengl: reference interop from sampler · d32fcb11
      Romain Vimont authored
      This allows to use an interop instance without a renderer.
      d32fcb11
    • Romain Vimont's avatar
      opengl: use the interop format in renderer · 8ab99b50
      Romain Vimont authored
      The interop initializes its own video_format_t from the input format.
      
      In the renderer initialization, always use this updated format. This
      avoids an additional format parameter, which may be confusing.
      8ab99b50
    • Romain Vimont's avatar
      opengl: simplify renderer format · 8eae3e87
      Romain Vimont authored
      The interop may modify its own copy of the video_format_t.
      
      These changes must be reported to the core (by writing to the provided
      video_format_t), except for the orientation: it is managed internally by
      OpenGL, so from the core point of view, the orientation does not change.
      
      Handle the format to report to the core outside of the renderer. This
      paves the way to pass only the interop to the renderer, without an
      additional video_format_t instance.
      8eae3e87
    • Romain Vimont's avatar
      opengl: move interop ownership to vgl · 736be666
      Romain Vimont authored
      The interop instances were owned by the renderers.
      
      To prepare for making the renderers independant of the input picture
      (in particular, independant of the interop), make the vgl own the
      interop instances.
      736be666
    • Romain Vimont's avatar
      opengl: extract renderer fields to sampler · bc009f91
      Romain Vimont authored
      Move the fields necessary to retrieve a picture pixel from its
      coordinates.
      bc009f91
    • Romain Vimont's avatar
      opengl: move fragment shader creation to renderer · b25fed96
      Romain Vimont authored
      Make the renderer create the fragment shader, using the vlc_texture()
      function generated by fragment_shader.c.
      b25fed96
    • Romain Vimont's avatar
      opengl: remove unused source format parameter · 44db220d
      Romain Vimont authored and Jean-Baptiste Kempf's avatar Jean-Baptiste Kempf committed
      
      
      The video_format_t parameter of vout_display_opengl_Display() is not
      used anymore. Remove it.
      Signed-off-by: Jean-Baptiste Kempf's avatarJean-Baptiste Kempf <jb@videolan.org>
      44db220d
    • Romain Vimont's avatar
      opengl: move paddings computation to _Prepare() · 10b59296
      Romain Vimont authored and Jean-Baptiste Kempf's avatar Jean-Baptiste Kempf committed
      
      
      Texture paddings were computed in _Display(), while the picture format
      is known in _Prepare().
      
      This will allow to remove the video_format_t parameter of _Display().
      Signed-off-by: Jean-Baptiste Kempf's avatarJean-Baptiste Kempf <jb@videolan.org>
      10b59296
    • Romain Vimont's avatar
      opengl: move down vlc_gl_renderer_Prepare() · b5a1afb2
      Romain Vimont authored and Jean-Baptiste Kempf's avatar Jean-Baptiste Kempf committed
      
      
      It will be modified to depend on static functions. Move it below them.
      
      This will make the diff more readable.
      Signed-off-by: Jean-Baptiste Kempf's avatarJean-Baptiste Kempf <jb@videolan.org>
      b5a1afb2
    • Romain Vimont's avatar
      opengl: merge successive loops · 22bfdc88
      Romain Vimont authored and Jean-Baptiste Kempf's avatar Jean-Baptiste Kempf committed
      
      
      After the previous changes, two successive loops iterating tex_count
      times can now be merged into one.
      Signed-off-by: Jean-Baptiste Kempf's avatarJean-Baptiste Kempf <jb@videolan.org>
      22bfdc88
    • Romain Vimont's avatar
      opengl: apply stereo transform using a matrix · b90d6aaf
      Romain Vimont authored and Jean-Baptiste Kempf's avatar Jean-Baptiste Kempf committed
      
      
      The multiview mode (stereo) was applied by changing the texture
      paddings to crop only the left eye.
      
      The problem is that these texture paddings are specific to the input
      picture, while the stereo mode is specific to the renderer, which should
      be independent of the input picture.
      
      To separate these concerns, apply the stereo mode using a matrix to
      transform the texture coordinates from the renderer.
      Signed-off-by: Jean-Baptiste Kempf's avatarJean-Baptiste Kempf <jb@videolan.org>
      b90d6aaf
    • Romain Vimont's avatar
      opengl: apply orientation in fragment shader · cb16845b
      Romain Vimont authored and Jean-Baptiste Kempf's avatar Jean-Baptiste Kempf committed
      
      
      Apply all texture coordinates transformation in the fragment shader.
      
      This is necessary to be able to implement a renderer independent of the
      input picture (i.e. without even knowing the details) by using a single
      GLSL function "vlc_texture(vec2 pic_coords)".
      Signed-off-by: Jean-Baptiste Kempf's avatarJean-Baptiste Kempf <jb@videolan.org>
      cb16845b
    • Romain Vimont's avatar
      opengl: setup coords once for all · d23e8e33
      Romain Vimont authored and Jean-Baptiste Kempf's avatar Jean-Baptiste Kempf committed
      
      
      Now that the coordinates are independant of paddings (which are
      transmitted via a separate transform matrix), there is no need to
      recompute them when the paddings change.
      Signed-off-by: Jean-Baptiste Kempf's avatarJean-Baptiste Kempf <jb@videolan.org>
      d23e8e33
    • Romain Vimont's avatar
      opengl: convert texture coords in fragment shader · bf4f21b5
      Romain Vimont authored and Jean-Baptiste Kempf's avatar Jean-Baptiste Kempf committed
      
      
      A picture is stored in OpenGL textures (one per plane), possibly with
      padding (the texture may be larger than the actual picture).
      
      The conversion from picture coordinates to texture coordinates (which
      takes the padding into account) was applied on the input coordinates,
      before the vertex shader. As a consequence, the vertex shader received
      one vector of input texture coordinates per plane (the padding is not
      necessarily the same for all the planes):
      
          (before this commit)
      
         picture   texture
         coords    coords        (attributes)      (varyings)
                (1 per plane)
      
                   (x0, y0) --> MultiTexCoord0     TexCoord0     fragment
         (x,y) --> (x1, y1) --> MultiTexCoord1 --> TexCoord1 --> shader
                   (x2, y2) --> MultiTexCoord2     TexCoord2
      
      This poses a problem to separate chroma conversion from rendering: the
      renderer should be able to retrieve a pixel color in picture
      coordinates, regarless of the input format or padding.
      
      To solve this issue, pass the picture coordinates instead of the texture
      coordinates as attribute, and initialize uniform matrices to convert
      from picture to texture coordinates for each plane directly in the
      fragment shader:
      
          (after this commit)
      
         picture
         coords    (attribute)     (varying)
      
         (x,y) --> PicCoordsIn --> PicCoords --> fragment shader
                                                   ^^^
                                                   |||
                                   TexCoordsMap0 --'||
                      (uniforms)   TexCoordsMap1 ---'|
                                   TexCoordsMap2 ----'
      
      Note that this also changes the multiplication order of
      (non-commutative) matrices, from (semantically):
      
          TexCoords = Orientation * TexCoordsMap * PicCoords
      
      to:
      
          TexCoords = TexCoordsMap * Orientation * PicCoords
      
      The latter is the correct one: the orientation defines how the input
      picture is rotated, so it must apply to picture coordinates, regardless
      of the actual coordinates in the texture.
      
      As a side effect, BuildRectangle, BuildSphere and BuildCube are now
      independant of both the number of planes and any texture padding.
      
      For now, TexCoordsMap is computed from the renderer, but the goal is to
      move it to a separate component (a "sampler").
      Signed-off-by: Jean-Baptiste Kempf's avatarJean-Baptiste Kempf <jb@videolan.org>
      bf4f21b5