gfx/angle/extensions/ANGLE_instanced_arrays.txt

Wed, 31 Dec 2014 06:09:35 +0100

author
Michael Schloh von Bennewitz <michael@schloh.com>
date
Wed, 31 Dec 2014 06:09:35 +0100
changeset 0
6474c204b198
permissions
-rw-r--r--

Cloned upstream origin tor-browser at tor-browser-31.3.0esr-4.5-1-build1
revision ID fc1c9ff7c1b2defdbc039f12214767608f46423f for hacking purpose.

     1 Name
     3     ANGLE_instanced_arrays
     5 Name Strings
     7     GL_ANGLE_instanced_arrays
     9 Contributors
    11     Contributors to ARB_instanced_arrays
    12     Nicolas Capens, TransGaming Inc.
    13     James Helferty, TransGaming Inc.
    14     Kenneth Russell, Google Inc.
    15     Vangelis Kokkevis, Google Inc.
    17 Contact
    19     Daniel Koch, TransGaming Inc. (daniel 'at' transgaming.com)
    21 Status
    23     Implemented in ANGLE r976.
    25 Version
    27     Last Modified Date: February 8, 2012
    28     Author Revision: 3
    30 Number
    32     OpenGL ES Extension #109
    34 Dependencies
    36     OpenGL ES 2.0 is required.
    38     This extension is written against the OpenGL ES 2.0 Specification.
    40 Overview
    42     A common use case in GL for some applications is to be able to
    43     draw the same object, or groups of similar objects that share
    44     vertex data, primitive count and type, multiple times.  This 
    45     extension provides a means of accelerating such use cases while 
    46     restricting the number of API calls, and keeping the amount of 
    47     duplicate data to a minimum.
    49     This extension introduces an array "divisor" for generic
    50     vertex array attributes, which when non-zero specifies that the
    51     attribute is "instanced."  An instanced attribute does not
    52     advance per-vertex as usual, but rather after every <divisor>
    53     conceptual draw calls.
    55     (Attributes which aren't instanced are repeated in their entirety
    56     for every conceptual draw call.)
    58     By specifying transform data in an instanced attribute or series
    59     of instanced attributes, vertex shaders can, in concert with the 
    60     instancing draw calls, draw multiple instances of an object with 
    61     one draw call.
    63 IP Status
    65     No known IP claims.
    67 New Tokens
    69     Accepted by the <pname> parameters of GetVertexAttribfv and 
    70     GetVertexAttribiv:
    72         VERTEX_ATTRIB_ARRAY_DIVISOR_ANGLE               0x88FE
    74 New Procedures and Functions
    76     void DrawArraysInstancedANGLE(enum mode, int first, sizei count,
    77             sizei primcount);
    79     void DrawElementsInstancedANGLE(enum mode, sizei count, enum type,
    80             const void *indices, sizei primcount);
    82     void VertexAttribDivisorANGLE(uint index, uint divisor);
    84 Additions to Chapter 2 of the OpenGL ES 2.0 Specification
    85 (OpenGL ES Operation)
    87     Modify section 2.8 (Vertex Arrays), p. 21
    89     After description of EnableVertexAttribArray / DisableVertexAttribArray
    90     add the following:
    92     "The command
    94         void VertexAttribDivisorANGLE(uint index, uint divisor);
    96     modifies the rate at which generic vertex attributes advance when
    97     rendering multiple instances of primitives in a single draw call
    98     (see DrawArraysInstancedANGLE and DrawElementsInstancedANGLE below).
    99     If <divisor> is zero, the attribute at slot <index> advances once
   100     per vertex.  If <divisor> is non-zero, the attribute advances once
   101     per <divisor> instances of the primitives being rendered.
   102     An attribute is referred to as "instanced" if its <divisor> value is
   103     non-zero."
   105     Replace the text describing DrawArrays and DrawElements in the
   106     "Transferring Array Elements" subsection of 2.8, from the second paragraph
   107     through the end of the section with the following:
   109     "The command
   111         void DrawArraysOneInstance( enum mode, int first, sizei count, int instance );
   113     does not exist in the GL, but is used to describe functionality in
   114     the rest of this section.  This function constructs a sequence of
   115     geometric primitives by transferring elements <first> through <first> +
   116     <count> - 1 of each enabled non-instanced array to the GL. <mode>
   117     specifies what kind of primitives are constructed, as defined in section
   118     2.6.1.
   120     If an enabled vertex attribute array is instanced (it has a non-zero
   121     attribute <divisor> as specified by VertexAttribDivisorANGLE), the element
   122     that is transferred to the GL is given by:
   124         floor( <instance> / <divisor> ).
   126     If an array corresponding to a generic attribute required by a vertex shader
   127     is not enabled, then the corresponding element is taken from the current
   128     generic attribute state (see section 2.7).
   130     If an array corresponding to a generic attribute required by a vertex shader
   131     is enabled, the corresponding current generic attribute value is unaffected 
   132     by the execution of DrawArraysOneInstance.
   134     Specifying <first> < 0 results in undefined behavior. Generating the error 
   135     INVALID_VALUE is recommended in this case.
   137     The command
   139         void DrawArrays( enum mode, int first, sizei count );
   141     is equivalent to the command sequence
   143         DrawArraysOneInstance(mode, first, count, 0);
   145     The command
   147         void DrawArraysInstancedANGLE(enum mode, int first, sizei count,
   148                 sizei primcount);
   150     behaves identically to DrawArrays except that <primcount>
   151     instances of the range of elements are executed, and the
   152     <instance> advances for each iteration. Instanced attributes that
   153     have <divisor> N, (where N > 0, as specified by
   154     VertexAttribDivisorANGLE) advance once every N instances.
   156     It has the same effect as: 
   158         if (mode, count, or primcount is invalid)
   159             generate appropriate error
   160         else {
   161             for (i = 0; i < primcount; i++) {
   162                 DrawArraysOneInstance(mode, first, count, i);
   163             }
   164         }
   166     The command
   168        void DrawElementsOneInstance( enum mode, sizei count, enum type,
   169             void *indices, int instance );
   171     does not exist in the GL, but is used to describe functionality in
   172     the rest of this section.  This command constructs a sequence of
   173     geometric primitives by successively transferring the <count> elements
   174     whose indices are stored in the currently bound element array buffer
   175     (see section 2.9.2) at the offset defined by <indices> to the GL.
   176     The <i>-th element transferred by DrawElementsOneInstance will be taken
   177     from element <indices>[i] of each enabled non-instanced array.
   178     <type> must be one of UNSIGNED_BYTE, UNSIGNED_SHORT, or UNSIGNED_INT, 
   179     indicating that the index values are of GL type ubyte, ushort, or uint
   180     respectively. <mode> specifies what kind of primitives are constructed,
   181     as defined in section 2.6.1.
   183     If an enabled vertex attribute array is instanced (it has a non-zero
   184     attribute <divisor> as specified by VertexAttribDivisorANGLE), the element
   185     that is transferred to the GL is given by:
   187         floor( <instance> / <divisor> );
   189     If an array corresponding to a generic attribute required by a vertex
   190     shader is not enabled, then the corresponding element is taken from the 
   191     current generic attribute state (see section 2.7). Otherwise, if an array
   192     is enabled, the corresponding current generic attribute value is 
   193     unaffected by the execution of DrawElementsOneInstance.
   195     The command
   197         void DrawElements( enum mode, sizei count, enum type,
   198              const void *indices);
   200     behaves identically to DrawElementsOneInstance with the <instance> 
   201     parameter set to zero; the effect of calling
   203         DrawElements(mode, count, type, indices);
   205     is equivalent to the command sequence:
   207        if (mode, count or type is invalid )
   208             generate appropriate error
   209         else
   210             DrawElementsOneInstance(mode, count, type, indices, 0);
   212     The command
   214         void DrawElementsInstancedANGLE(enum mode, sizei count, enum type,
   215                 const void *indices, sizei primcount);
   217     behaves identically to DrawElements except that <primcount>
   218     instances of the set of elements are executed and the instance
   219     advances between each set. Instanced attributes are advanced as they do
   220     during the execution of DrawArraysInstancedANGLE. It has the same effect as:
   222         if (mode, count, primcount, or type is invalid )
   223             generate appropriate error
   224         else {
   225             for (int i = 0; i < primcount; i++) {
   226                 DrawElementsOneInstance(mode, count, type, indices, i);
   227             }
   228         }
   230     If the number of supported generic vertex attributes (the value of 
   231     MAX_VERTEX_ATTRIBS) is <n>, then the client state required to implement
   232     vertex arrays consists of <n> boolean values, <n> memory pointers, <n>
   233     integer stride values, <n> symbolic constants representing array types,
   234     <n> integers representing values per element, <n> boolean values 
   235     indicating normalization, and <n> integers representing vertex attribute
   236     divisors. 
   238     In the initial state, the boolean values are each false, the memory
   239     pointers are each NULL, the strides are each zero, the array types are 
   240     each FLOAT, the integers representing values per element are each four,
   241     and the divisors are each zero."
   243 Additions to Chapter 3 of the OpenGL ES 2.0 Specification (Rasterization)
   245     None
   247 Additions to Chapter 4 of the OpenGL ES 2.0 Specification (Per-Fragment
   248 Operations and the Framebuffer)
   250     None
   252 Additions to Chapter 5 of the OpenGL ES 2.0 Specification (Special Functions)
   254     None
   256 Additions to Chapter 6 of the OpenGL ES 2.0 Specification (State and State
   257 Requests)
   259     In section 6.1.8, add VERTEX_ATTRIB_ARRAY_DIVISOR_ANGLE to the list of 
   260     pnames accepted by GetVertexAttribfv and GetVertexAttribiv.
   262 Additions to the AGL/EGL/GLX/WGL Specifications
   264     None
   266 Dependencies on OES_element_index_uint
   268     If OES_element_index_uint is not supported, removed all references
   269     to UNSIGNED_INT indices and the associated GL data type uint in 
   270     the description of DrawElementsOneInstance.
   272 Errors
   274     INVALID_VALUE is generated by VertexAttribDivisorANGLE if <index>
   275     is greater than or equal to MAX_VERTEX_ATTRIBS.
   277     INVALID_ENUM is generated by DrawElementsInstancedANGLE if <type> is
   278     not one of UNSIGNED_BYTE, UNSIGNED_SHORT or UNSIGNED_INT.
   280     INVALID_VALUE is generated by DrawArraysInstancedANGLE if <first>,
   281     <count>, or <primcount> is less than zero.
   283     INVALID_ENUM is generated by DrawArraysInstancedANGLE or 
   284     DrawElementsInstancedANGLE if <mode> is not one of the modes described in
   285     section 2.6.1.
   287     INVALID_VALUE is generated by DrawElementsInstancedANGLE if <count> or
   288     <primcount> is less than zero.
   290     INVALID_OPERATION is generated by DrawArraysInstancedANGLE or 
   291     DrawElementsInstancedANGLE if there is not at least one enabled
   292     vertex attribute array that has a <divisor> of zero and is bound to an
   293     active generic attribute value in the program used for the draw command.
   295 New State
   297     Changes to table 6.7, p. 268 (Vertex Array Data)
   299                                                                Initial
   300     Get Value                          Type   Get Command      Value    Description       Sec.  
   301     ---------                          -----  -----------      -------  -----------       ----
   302     VERTEX_ATTRIB_ARRAY_DIVISOR_ANGLE  8*xZ+  GetVertexAttrib  0        Instance Divisor  2.8
   304 Issues
   306     1) Should vertex attribute zero be instance-able?
   308        Resolved: Yes. 
   309        Discussion: In Direct3D 9 stream 0 must be specified as indexed data
   310        and it cannot be instanced. In ANGLE we can work around this by
   311        remapping any other stream that does have indexed data (ie a zero
   312        attribute divisor) to stream 0 in D3D9. This works because the HLSL
   313        vertex shader matches attributes against the stream by using the 
   314        shader semantic index.
   316     2) Can all vertex attributes be instanced simultaneously?
   318        Resolved: No
   319        Discussion: In rare cases it is possible for no attribute to have a 
   320        divisor of 0, meaning that all attributes are instanced and none of
   321        them are regularly indexed. This in turn means each instance can only
   322        have a single position element, and so it only actually renders
   323        something when rendering point primitives. This is not a very 
   324        meaningful way of using instancing (which is likely why D3D restricts
   325        stream 0 to be indexed regularly for position data in the first place).
   326        We could implement it by drawing these points one at a time (essentially
   327        emulating instancing), but it would not be very efficient and there
   328        seems to be little-to-no value in doing so.
   330        If all of the enabled vertex attribute arrays that are bound to active
   331        generic attributes in the program have a non-zero divisor, the draw
   332        call should return INVALID_OPERATION.
   334     3) Direct3D 9 only supports instancing for DrawIndexedPrimitive which
   335        corresponds to DrawElementsInstanced.  Should we support 
   336        DrawArraysInstanced?
   338        Resolved: Yes
   339        Discussion: This can be supported easily enough by simply manufacturing
   340        a linear index buffer of sufficient size and using that to do indexed
   341        D3D9 drawing.
   343     4) How much data is needed in a buffer for an instanced attribute?
   345        Resolved: Where stride is the value passed to VertexAttribPointer:
   347        if stride > 0
   348          size = stride * ceil(primcount / divisor);
   349        else
   350          size = elementsize * ceil(primcount / divisor);
   352 Revision History
   354     #3 February 8, 2012 dgkoch
   355        - clarify Issue 3 and the error condition for no indexed attributes
   356     #2 January 24, 2012 dgkoch
   357        - fix typos, add clarifications, and more errors
   358     #1 January 17, 2012 dgkoch
   359        - initial GLES2 version from ARB_instanced_arrays

mercurial