Welcome to mirror list, hosted at ThFree Co, Russian Federation.

gpu.1.py « examples « python_api « doc - git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
blob: 1ffa0a58856e96b387f6816f67609e9dd43ef60d (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
"""
Geometry Batches
++++++++++++++++

To draw geometry using the gpu module you need to create a :class:`gpu.types.GPUBatch` object.
Batches contain a sequence of points, lines or triangles and associated geometry attributes.

A batch can be drawn multiple times, so they should be cached whenever possible.
This makes them much faster than using the legacy `glBegin` and `glEnd` method, which would recreate the geometry data every time.

Every batch has a so called `Vertex Buffer`.
It contains the attributes for every vertex.
Typical attributes are `position`, `color` and `uv`.
Which attributes the vertex buffer of a batch contains, depends on the shader that will be used to process the batch. The best way to create a new batch is to use the :class:`gpu_extras.batch.batch_for_shader` function.

Furthermore, when creating a new batch, you have to specify the draw type.
The most used types are ``POINTS``, ``LINES`` and ``TRIS``.

Shaders
+++++++

A shader is a small program that tells the GPU how to draw batch geometry.
There are a couple of built-in shaders for the most common tasks.
Built-in shaders can be accessed with :class:`gpu.shader.from_builtin`.
Every built-in shader has an identifier (e.g. `2D_UNIFORM_COLOR` and `3D_FLAT_COLOR`).

Custom shaders can be used as well.
The :class:`gpu.types.GPUShader` takes the shader code as input and compiles it.
Every shader has at least a vertex and a fragment shader.
Optionally a geometry shader can be used as well.

.. note::
   A `GPUShader` is actually a `program` in OpenGL terminology.

Shaders define a set of `uniforms` and `attributes`.
**Uniforms** are properties that are constant for every vertex in a batch.
They have to be set before the batch but after the shader has been bound.
**Attributes** are properties that can be different for every vertex.

The attributes and uniforms used by built-in shaders are listed here: :class:`gpu.shader`

A batch can only be processed/drawn by a shader when it provides all the attributes that the shader specifies.

Vertex Buffers
++++++++++++++

A vertex buffer is an array that contains the attributes for every vertex.
To create a new vertex buffer (:class:`gpu.types.GPUVertBuf`) you have to provide two things: 1) the amount of vertices in the buffer and 2) the format of the buffer.

The format (:class:`gpu.types.GPUVertFormat`) describes which attributes are stored in the buffer.
E.g. to create a vertex buffer that contains 6 vertices, each with a position and a normal could look like so::

    import gpu
    vertex_positions = [(0, 0, 0), ...]
    vertex_normals = [(0, 0, 1), ...]

    fmt = gpu.types.GPUVertFormat()
    fmt.attr_add(id="pos", comp_type='F32', len=3, fetch_mode='FLOAT')
    fmt.attr_add(id="normal", comp_type='F32', len=3, fetch_mode='FLOAT')

    vbo = gpu.types.GPUVertBuf(len=6, format=fmt)
    vbo.attr_fill(id="pos", data=vertex_positions)
    vbo.attr_fill(id="normal", data=vertex_normals)

    batch = gpu.types.GPUBatch(type='TRIS', buf=vbo)

This batch contains two triangles now.
Vertices 0-2 describe the first and vertices 3-5 the second triangle.

.. note::
    The recommended way to create batches is to use the :class:`gpu_extras.batch.batch_for_shader` function. It makes sure that you provide all the vertex attributes that are necessary to be able to use a specific shader.

Index Buffers
+++++++++++++

The main reason why index buffers exist is to reduce the amount of memory required to store and send geometry.
E.g. often the same vertex is used by multiple triangles in a mesh.
Instead of vertex attributes multiple times to the gpu, an index buffer can be used.
An index buffer is an array of integers that describes in which order the vertex buffer should be read.
E.g. when you have a vertex buffer ``[a, b, c]`` and an index buffer ``[0, 2, 1, 2, 1, 0]`` it is like if you just had the vertex buffer ``[a, c, b, c, b, a]``.
Using an index buffer saves memory because usually a single integer is smaller than all attributes for one vertex combined.

Index buffers can be used like so::

    indices = [(0, 1), (2, 0), (2, 3), ...]
    ibo = gpu.types.GPUIndexBuf(type='LINES', seq=indices)
    batch = gpu.types.GPUBatch(type='LINES', buf=vbo, elem=ibo)

.. note::
    Instead of creating index buffers object manually, you can also just use the optional `indices` parameter of the :class:`gpu_extras.batch.batch_for_shader` function.

Offscreen Rendering
+++++++++++++++++++

Everytime something is drawn, the result is written into a framebuffer.
Usually this buffer will later be displayed on the screen.
However, sometimes you might want to draw into a separate "texture" and use it further.
E.g. you could use the render result as a texture on another object or save the rendered result on disk.
Offscreen Rendering is done using the :class:`gpu.types.GPUOffScreen` type.

.. warning::
    ``GPUOffScreen`` objects are bound to the opengl context they have been created in.
    This also means that once Blender discards this context (i.e. a window is closed) the offscreen instance will also be freed.


Examples
++++++++

To try these examples, just copy them into Blenders text editor and execute them.
To keep the examples relatively small, they just register a draw function that can't easily be removed anymore.
Blender has to be restarted in order to delete the draw handlers.
"""