basilisk-engine 0.1.2__py3-none-any.whl → 0.1.3__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of basilisk-engine might be problematic. Click here for more details.

Files changed (82) hide show
  1. basilisk/__init__.py +11 -11
  2. basilisk/bsk_assets/cube.obj +48 -48
  3. basilisk/collisions/broad/broad_aabb.py +102 -102
  4. basilisk/collisions/broad/broad_bvh.py +137 -137
  5. basilisk/collisions/collider.py +95 -83
  6. basilisk/collisions/collider_handler.py +225 -228
  7. basilisk/collisions/narrow/contact_manifold.py +90 -90
  8. basilisk/collisions/narrow/dataclasses.py +33 -27
  9. basilisk/collisions/narrow/deprecated.py +46 -46
  10. basilisk/collisions/narrow/epa.py +91 -91
  11. basilisk/collisions/narrow/gjk.py +66 -66
  12. basilisk/collisions/narrow/graham_scan.py +24 -24
  13. basilisk/collisions/narrow/helper.py +29 -29
  14. basilisk/collisions/narrow/line_intersections.py +106 -106
  15. basilisk/collisions/narrow/sutherland_hodgman.py +75 -75
  16. basilisk/config.py +2 -2
  17. basilisk/draw/draw.py +100 -100
  18. basilisk/draw/draw_handler.py +180 -210
  19. basilisk/draw/font_renderer.py +28 -28
  20. basilisk/engine.py +195 -195
  21. basilisk/generic/abstract_bvh.py +15 -15
  22. basilisk/generic/abstract_custom.py +133 -133
  23. basilisk/generic/collisions.py +70 -70
  24. basilisk/generic/input_validation.py +67 -28
  25. basilisk/generic/math.py +6 -6
  26. basilisk/generic/matrices.py +33 -33
  27. basilisk/generic/meshes.py +72 -72
  28. basilisk/generic/quat.py +137 -137
  29. basilisk/generic/quat_methods.py +7 -7
  30. basilisk/generic/raycast_result.py +24 -0
  31. basilisk/generic/vec3.py +143 -143
  32. basilisk/input/mouse.py +61 -59
  33. basilisk/mesh/cube.py +33 -33
  34. basilisk/mesh/mesh.py +230 -230
  35. basilisk/mesh/mesh_from_data.py +132 -132
  36. basilisk/mesh/model.py +271 -271
  37. basilisk/mesh/narrow_aabb.py +89 -89
  38. basilisk/mesh/narrow_bvh.py +91 -91
  39. basilisk/mesh/narrow_primative.py +23 -23
  40. basilisk/nodes/helper.py +29 -0
  41. basilisk/nodes/node.py +681 -617
  42. basilisk/nodes/node_handler.py +95 -118
  43. basilisk/particles/particle_handler.py +63 -54
  44. basilisk/particles/particle_renderer.py +87 -87
  45. basilisk/physics/impulse.py +112 -112
  46. basilisk/physics/physics_body.py +43 -43
  47. basilisk/physics/physics_engine.py +35 -35
  48. basilisk/render/batch.py +86 -86
  49. basilisk/render/camera.py +204 -199
  50. basilisk/render/chunk.py +99 -99
  51. basilisk/render/chunk_handler.py +154 -154
  52. basilisk/render/frame.py +181 -181
  53. basilisk/render/image.py +75 -75
  54. basilisk/render/image_handler.py +122 -122
  55. basilisk/render/light.py +96 -96
  56. basilisk/render/light_handler.py +58 -58
  57. basilisk/render/material.py +219 -219
  58. basilisk/render/material_handler.py +135 -135
  59. basilisk/render/shader.py +109 -109
  60. basilisk/render/shader_handler.py +79 -79
  61. basilisk/render/sky.py +120 -120
  62. basilisk/scene.py +250 -210
  63. basilisk/shaders/batch.frag +276 -276
  64. basilisk/shaders/batch.vert +115 -115
  65. basilisk/shaders/draw.frag +21 -21
  66. basilisk/shaders/draw.vert +21 -21
  67. basilisk/shaders/filter.frag +22 -22
  68. basilisk/shaders/frame.frag +12 -12
  69. basilisk/shaders/frame.vert +13 -13
  70. basilisk/shaders/geometry.frag +8 -8
  71. basilisk/shaders/geometry.vert +41 -41
  72. basilisk/shaders/normal.frag +59 -59
  73. basilisk/shaders/normal.vert +96 -96
  74. basilisk/shaders/particle.frag +71 -71
  75. basilisk/shaders/particle.vert +84 -84
  76. basilisk/shaders/sky.frag +9 -9
  77. basilisk/shaders/sky.vert +13 -13
  78. {basilisk_engine-0.1.2.dist-info → basilisk_engine-0.1.3.dist-info}/METADATA +45 -38
  79. basilisk_engine-0.1.3.dist-info/RECORD +97 -0
  80. {basilisk_engine-0.1.2.dist-info → basilisk_engine-0.1.3.dist-info}/WHEEL +1 -1
  81. basilisk_engine-0.1.2.dist-info/RECORD +0 -95
  82. {basilisk_engine-0.1.2.dist-info → basilisk_engine-0.1.3.dist-info}/top_level.txt +0 -0
basilisk/render/camera.py CHANGED
@@ -1,200 +1,205 @@
1
- import pygame as pg
2
- import glm
3
- import numpy as np
4
-
5
- # Camera view constants
6
- FOV = 50 # Degrees
7
- NEAR = 0.1
8
- FAR = 350
9
-
10
- # Camera movement constants
11
- SPEED = 10
12
- SENSITIVITY = 0.15
13
-
14
- class Camera:
15
- engine: ...
16
- """Back reference to the parent engine"""
17
- scene: ...
18
- """Back reference to the parent scene"""
19
- aspect_ratio: float
20
- """Aspect ratio of the engine window"""
21
- position: glm.vec3
22
- """Location of the camera (maters)"""
23
-
24
- def __init__(self, position=(0, 0, 20), yaw=-90, pitch=0) -> None:
25
- """
26
- Camera object to get view and projection matricies. Movement built in
27
- """
28
- # Back references
29
- self.scene = None
30
- self.engine = None
31
- # The initial aspect ratio of the screen
32
- self.aspect_ratio = 1.0
33
- # Position
34
- self.position = glm.vec3(position)
35
- # k vector for vertical movement
36
- self.UP = glm.vec3(0, 1, 0)
37
- # Movement vectors
38
- self.up = glm.vec3(0, 1, 0)
39
- self.right = glm.vec3(1, 0, 0)
40
- self.forward = glm.vec3(0, 0, -1)
41
- # Look directions in degrees
42
- self.yaw = yaw
43
- self.pitch = pitch
44
- # View matrix
45
- self.m_view = self.get_view_matrix()
46
- # Projection matrix
47
- self.m_proj = self.get_projection_matrix()
48
-
49
- def update(self) -> None:
50
- """
51
- Updates the camera view matrix
52
- """
53
-
54
- self.update_camera_vectors()
55
- self.m_view = self.get_view_matrix()
56
-
57
- def update_camera_vectors(self) -> None:
58
- """
59
- Computes the forward vector based on the pitch and yaw. Computes horizontal and vertical vectors with cross product.
60
- """
61
- yaw, pitch = glm.radians(self.yaw), glm.radians(self.pitch)
62
-
63
- self.forward.x = glm.cos(yaw) * glm.cos(pitch)
64
- self.forward.y = glm.sin(pitch)
65
- self.forward.z = glm.sin(yaw) * glm.cos(pitch)
66
-
67
- self.forward = glm.normalize(self.forward)
68
- self.right = glm.normalize(glm.cross(self.forward, self.UP))
69
- self.up = glm.normalize(glm.cross(self.right, self.forward))
70
-
71
- def use(self):
72
- # Updated aspect ratio of the screen
73
- self.aspect_ratio = self.engine.win_size[0] / self.engine.win_size[1]
74
- # View matrix
75
- self.m_view = self.get_view_matrix()
76
- # Projection matrix
77
- self.m_proj = self.get_projection_matrix()
78
-
79
- def get_view_matrix(self) -> glm.mat4x4:
80
- return glm.lookAt(self.position, self.position + self.forward, self.up)
81
-
82
- def get_projection_matrix(self) -> glm.mat4x4:
83
- return glm.perspective(glm.radians(FOV), self.aspect_ratio, NEAR, FAR)
84
-
85
- def get_params(self) -> tuple:
86
- return self.engine, self.position, self.yaw, self.pitch
87
-
88
- def look_at(self, other) -> None:
89
- forward = glm.normalize(other.position - self.position)
90
- self.yaw = np.degrees(np.arctan2(forward.z, forward.x))
91
- self.pitch = np.degrees(np.arctan2(forward.y, np.sqrt(forward.x ** 2 + forward.z ** 2)))
92
-
93
- def __repr__(self):
94
- return f'<Basilisk Camera | Position: {self.position}, Direction: {self.forward}>'
95
-
96
- @property
97
- def scene(self): return self._scene
98
- @property
99
- def position(self): return self._position
100
- @property
101
- def direction(self): return self.forward
102
-
103
- @scene.setter
104
- def scene(self, value):
105
- if value == None: return
106
- self._scene = value
107
- self.engine = self._scene.engine
108
- self.use()
109
- @position.setter
110
- def position(self, value: tuple | list | glm.vec3 | np.ndarray):
111
- if isinstance(value, glm.vec3): self._position = glm.vec3(value)
112
- elif isinstance(value, tuple) or isinstance(value, list) or isinstance(value, np.ndarray):
113
- if len(value) != 3: raise ValueError(f'Camera: Invalid number of values for position. Expected 3, got {len(value)}')
114
- self._position = glm.vec3(value)
115
- else: raise TypeError(f'Camera: Invalid position value type {type(value)}')
116
- @direction.setter
117
- def direction(self, value: tuple | list | glm.vec3 | np.ndarray):
118
- if isinstance(value, glm.vec3): self.direction = glm.normalize(glm.vec3(value))
119
- elif isinstance(value, tuple) or isinstance(value, list) or isinstance(value, np.ndarray):
120
- if len(value) != 3: raise ValueError(f'Camera: Invalid number of values for direction. Expected 3, got {len(value)}')
121
- self.forward = glm.normalize(glm.vec3(value))
122
- else: raise TypeError(f'Camera: Invalid direction value type {type(value)}')
123
-
124
-
125
- class FreeCamera(Camera):
126
- def __init__(self, position=(0, 0, 20), yaw=-90, pitch=0):
127
- super().__init__(position, yaw, pitch)
128
-
129
- def update(self) -> None:
130
- """
131
- Updates the camera position and rotaiton based on user input
132
- """
133
-
134
- self.move()
135
- self.rotate()
136
- self.update_camera_vectors()
137
- self.m_view = self.get_view_matrix()
138
-
139
- def rotate(self) -> None:
140
- """
141
- Rotates the camera based on the amount of mouse movement.
142
- """
143
- rel_x, rel_y = pg.mouse.get_rel()
144
- self.yaw += rel_x * SENSITIVITY
145
- self.pitch -= rel_y * SENSITIVITY
146
- self.yaw = self.yaw % 360
147
- self.pitch = max(-89, min(89, self.pitch))
148
-
149
- def move(self) -> None:
150
- """
151
- Checks for button presses and updates vectors accordingly.
152
- """
153
- velocity = (SPEED + self.engine.keys[pg.K_CAPSLOCK] * 10) * self.engine.delta_time
154
- keys = self.engine.keys
155
- if keys[pg.K_w]:
156
- self.position += glm.normalize(glm.vec3(self.forward.x, 0, self.forward.z)) * velocity
157
- if keys[pg.K_s]:
158
- self.position -= glm.normalize(glm.vec3(self.forward.x, 0, self.forward.z)) * velocity
159
- if keys[pg.K_a]:
160
- self.position -= self.right * velocity
161
- if keys[pg.K_d]:
162
- self.position += self.right * velocity
163
- if keys[pg.K_SPACE]:
164
- self.position += self.UP * velocity
165
- if keys[pg.K_LSHIFT]:
166
- self.position -= self.UP * velocity
167
-
168
-
169
- class FollowCamera(FreeCamera):
170
- def __init__(self, parent, position=(0, 0, 20), yaw=-90, pitch=0, offset=(0, 0, 0)):
171
- super().__init__(position, yaw, pitch)
172
- self.parent = parent
173
- self.offest = glm.vec3(offset)
174
-
175
- def move(self) -> None:
176
- """
177
- Moves the camera to the parent node
178
- """
179
-
180
- self.position = self.parent.position + self.offest
181
-
182
- class OrbitCamera(FreeCamera):
183
- def __init__(self, parent, position=(0, 0, 20), yaw=-90, pitch=0, distance=5):
184
- self.parent = parent
185
- self.distance = distance
186
- super().__init__(position, yaw, pitch)
187
-
188
- def get_view_matrix(self) -> glm.mat4x4:
189
- return glm.lookAt(self.position, self.parent.position, self.up)
190
-
191
- def move(self) -> None:
192
- """
193
- Moves the camera to the parent node
194
- """
195
-
196
- self.position = self.parent.position - glm.normalize(self.forward) * self.distance
197
-
198
- class StaticCamera(Camera):
199
- def __init__(self, position=(0, 0, 20), yaw=-90, pitch=0):
1
+ import pygame as pg
2
+ import glm
3
+ import numpy as np
4
+
5
+ # Camera view constants
6
+ FOV = 50 # Degrees
7
+ NEAR = 0.1
8
+ FAR = 350
9
+
10
+ # Camera movement constants
11
+ SPEED = 10
12
+ SENSITIVITY = 0.15
13
+
14
+ class Camera:
15
+ engine: ...
16
+ """Back reference to the parent engine"""
17
+ scene: ...
18
+ """Back reference to the parent scene"""
19
+ aspect_ratio: float
20
+ """Aspect ratio of the engine window"""
21
+ position: glm.vec3
22
+ """Location of the camera (maters)"""
23
+
24
+ def __init__(self, position=(0, 0, 20), yaw=-90, pitch=0) -> None:
25
+ """
26
+ Camera object to get view and projection matricies. Movement built in
27
+ """
28
+ # Back references
29
+ self.scene = None
30
+ self.engine = None
31
+ # The initial aspect ratio of the screen
32
+ self.aspect_ratio = 1.0
33
+ # Position
34
+ self.position = glm.vec3(position)
35
+ # k vector for vertical movement
36
+ self.UP = glm.vec3(0, 1, 0)
37
+ # Movement vectors
38
+ self.up = glm.vec3(0, 1, 0)
39
+ self.right = glm.vec3(1, 0, 0)
40
+ self.forward = glm.vec3(0, 0, -1)
41
+ # Look directions in degrees
42
+ self.yaw = yaw
43
+ self.pitch = pitch
44
+ # View matrix
45
+ self.m_view = self.get_view_matrix()
46
+ # Projection matrix
47
+ self.m_proj = self.get_projection_matrix()
48
+
49
+ def update(self) -> None:
50
+ """
51
+ Updates the camera view matrix
52
+ """
53
+
54
+ self.update_camera_vectors()
55
+ self.m_view = self.get_view_matrix()
56
+
57
+ def update_camera_vectors(self) -> None:
58
+ """
59
+ Computes the forward vector based on the pitch and yaw. Computes horizontal and vertical vectors with cross product.
60
+ """
61
+ yaw, pitch = glm.radians(self.yaw), glm.radians(self.pitch)
62
+
63
+ self.forward.x = glm.cos(yaw) * glm.cos(pitch)
64
+ self.forward.y = glm.sin(pitch)
65
+ self.forward.z = glm.sin(yaw) * glm.cos(pitch)
66
+
67
+ self.forward = glm.normalize(self.forward)
68
+ self.right = glm.normalize(glm.cross(self.forward, self.UP))
69
+ self.up = glm.normalize(glm.cross(self.right, self.forward))
70
+
71
+ def use(self):
72
+ # Updated aspect ratio of the screen
73
+ self.aspect_ratio = self.engine.win_size[0] / self.engine.win_size[1]
74
+ # View matrix
75
+ self.m_view = self.get_view_matrix()
76
+ # Projection matrix
77
+ self.m_proj = self.get_projection_matrix()
78
+
79
+ def get_view_matrix(self) -> glm.mat4x4:
80
+ return glm.lookAt(self.position, self.position + self.forward, self.up)
81
+
82
+ def get_projection_matrix(self) -> glm.mat4x4:
83
+ return glm.perspective(glm.radians(FOV), self.aspect_ratio, NEAR, FAR)
84
+
85
+ def get_params(self) -> tuple:
86
+ return self.engine, self.position, self.yaw, self.pitch
87
+
88
+ def look_at(self, other) -> None:
89
+ forward = glm.normalize(other.position - self.position)
90
+ self.yaw = np.degrees(np.arctan2(forward.z, forward.x))
91
+ self.pitch = np.degrees(np.arctan2(forward.y, np.sqrt(forward.x ** 2 + forward.z ** 2)))
92
+
93
+ def __repr__(self):
94
+ return f'<Basilisk Camera | Position: {self.position}, Direction: {self.forward}>'
95
+
96
+ @property
97
+ def scene(self): return self._scene
98
+ @property
99
+ def position(self): return self._position
100
+ @property
101
+ def direction(self): return self.forward
102
+ @property
103
+ def horizontal(self): return glm.normalize(self.forward.xz)
104
+
105
+ @scene.setter
106
+ def scene(self, value):
107
+ if value == None: return
108
+ self._scene = value
109
+ self.engine = self._scene.engine
110
+ self.use()
111
+
112
+ @position.setter
113
+ def position(self, value: tuple | list | glm.vec3 | np.ndarray):
114
+ if isinstance(value, glm.vec3): self._position = glm.vec3(value)
115
+ elif isinstance(value, tuple) or isinstance(value, list) or isinstance(value, np.ndarray):
116
+ if len(value) != 3: raise ValueError(f'Camera: Invalid number of values for position. Expected 3, got {len(value)}')
117
+ self._position = glm.vec3(value)
118
+ else: raise TypeError(f'Camera: Invalid position value type {type(value)}')
119
+
120
+ @direction.setter
121
+ def direction(self, value: tuple | list | glm.vec3 | np.ndarray):
122
+ if isinstance(value, glm.vec3): self.direction = glm.normalize(glm.vec3(value))
123
+ elif isinstance(value, tuple) or isinstance(value, list) or isinstance(value, np.ndarray):
124
+ if len(value) != 3: raise ValueError(f'Camera: Invalid number of values for direction. Expected 3, got {len(value)}')
125
+ self.forward = glm.normalize(glm.vec3(value))
126
+ else: raise TypeError(f'Camera: Invalid direction value type {type(value)}')
127
+
128
+
129
+ class FreeCamera(Camera):
130
+ def __init__(self, position=(0, 0, 20), yaw=-90, pitch=0):
131
+ super().__init__(position, yaw, pitch)
132
+
133
+ def update(self) -> None:
134
+ """
135
+ Updates the camera position and rotaiton based on user input
136
+ """
137
+
138
+ self.move()
139
+ self.rotate()
140
+ self.update_camera_vectors()
141
+ self.m_view = self.get_view_matrix()
142
+
143
+ def rotate(self) -> None:
144
+ """
145
+ Rotates the camera based on the amount of mouse movement.
146
+ """
147
+ rel_x, rel_y = pg.mouse.get_rel()
148
+ self.yaw += rel_x * SENSITIVITY
149
+ self.pitch -= rel_y * SENSITIVITY
150
+ self.yaw = self.yaw % 360
151
+ self.pitch = max(-89, min(89, self.pitch))
152
+
153
+ def move(self) -> None:
154
+ """
155
+ Checks for button presses and updates vectors accordingly.
156
+ """
157
+ velocity = (SPEED + self.engine.keys[pg.K_CAPSLOCK] * 10) * self.engine.delta_time
158
+ keys = self.engine.keys
159
+ if keys[pg.K_w]:
160
+ self.position += glm.normalize(glm.vec3(self.forward.x, 0, self.forward.z)) * velocity
161
+ if keys[pg.K_s]:
162
+ self.position -= glm.normalize(glm.vec3(self.forward.x, 0, self.forward.z)) * velocity
163
+ if keys[pg.K_a]:
164
+ self.position -= self.right * velocity
165
+ if keys[pg.K_d]:
166
+ self.position += self.right * velocity
167
+ if keys[pg.K_SPACE]:
168
+ self.position += self.UP * velocity
169
+ if keys[pg.K_LSHIFT]:
170
+ self.position -= self.UP * velocity
171
+
172
+
173
+ class FollowCamera(FreeCamera):
174
+ def __init__(self, parent, position=(0, 0, 20), yaw=-90, pitch=0, offset=(0, 0, 0)):
175
+ super().__init__(position, yaw, pitch)
176
+ self.parent = parent
177
+ self.offest = glm.vec3(offset)
178
+
179
+ def move(self) -> None:
180
+ """
181
+ Moves the camera to the parent node
182
+ """
183
+
184
+ self.position = self.parent.position + self.offest
185
+
186
+ class OrbitCamera(FreeCamera):
187
+ def __init__(self, parent, position=(0, 0, 20), yaw=-90, pitch=0, distance=5, offset=(0, 0)):
188
+ self.parent = parent
189
+ self.distance = distance
190
+ self.offset = glm.vec2(offset)
191
+ super().__init__(position, yaw, pitch)
192
+
193
+ def get_view_matrix(self) -> glm.mat4x4:
194
+ return glm.lookAt(self.position, self.parent.position, self.up)
195
+
196
+ def move(self) -> None:
197
+ """
198
+ Moves the camera to the parent node
199
+ """
200
+
201
+ self.position = self.parent.position - glm.normalize(self.forward) * self.distance
202
+
203
+ class StaticCamera(Camera):
204
+ def __init__(self, position=(0, 0, 20), yaw=-90, pitch=0):
200
205
  super().__init__(position, yaw, pitch)
basilisk/render/chunk.py CHANGED
@@ -1,100 +1,100 @@
1
- from .batch import Batch
2
-
3
-
4
- class Chunk():
5
- chunk_handler: ...
6
- """Back refrence to the parent chunk handler"""
7
- position: tuple
8
- """The position of the chunk. Used as a key in the chunk handler"""
9
- batch: Batch
10
- """Batched mesh of the chunk"""
11
- nodes: set
12
- """Set conaining references to all nodes in the chunk"""
13
- static: bool
14
- """Type of node that the chunk recognizes"""
15
-
16
- def __init__(self, chunk_handler, position: tuple, static: bool, shader=None) -> None:
17
- """
18
- Basilisk chunk object.
19
- Contains references to all nodes in the chunk.
20
- Handles batching for its own nodes
21
- """
22
-
23
- # Back references
24
- self.chunk_handler = chunk_handler
25
-
26
- # Chunk Attrbiutes
27
- self.position = position
28
- self.static = static
29
- self.shader = shader
30
-
31
- # Create empty batch
32
- self.batch = Batch(self)
33
-
34
- # Create empty set for chunk's nodes
35
- self.nodes = set()
36
-
37
- def render(self) -> None:
38
- """
39
- Renders the chunk mesh
40
- """
41
-
42
- if self.batch.vao: self.batch.vao.render()
43
-
44
- def update(self) -> bool:
45
- """
46
- Batches all the node meshes in the chunk
47
- """
48
-
49
- # Check if there are no nodes in the chunk
50
- if not self.nodes: return False
51
- # Batch the chunk nodes, return success bit
52
- return self.batch.batch()
53
-
54
- def node_update_callback(self, node):
55
- if not self.batch.vbo: return
56
-
57
- data = node.get_data()
58
- self.batch.vbo.write(data, node.data_index * 25 * 4)
59
-
60
- def add(self, node):
61
- """
62
- Adds an existing node to the chunk. Updates the node's chunk reference
63
- """
64
-
65
- self.nodes.add(node)
66
- node.chunk = self
67
-
68
- return node
69
-
70
- def remove(self, node):
71
- """
72
- Removes a node from the chunk
73
- """
74
-
75
- if node == None: return
76
-
77
- self.nodes.remove(node)
78
- if self.batch and self.batch.vbo: self.batch.vbo.clear()
79
-
80
- return node
81
-
82
- def get_program(self):
83
- """
84
- Gets the program of the chunks nodes' shader
85
- """
86
-
87
- shader = self.shader
88
-
89
- if shader: return shader.program
90
- return self.chunk_handler.engine.shader.program
91
-
92
- def __repr__(self) -> str:
93
- return f'<Basilisk Chunk | {self.position}, {len(self.nodes)} nodes, {"static" if self.static else "dynamic"}>'
94
-
95
- def __del__(self) -> None:
96
- """
97
- Deletes the batch if this chunk is deleted
98
- """
99
-
1
+ from .batch import Batch
2
+
3
+
4
+ class Chunk():
5
+ chunk_handler: ...
6
+ """Back refrence to the parent chunk handler"""
7
+ position: tuple
8
+ """The position of the chunk. Used as a key in the chunk handler"""
9
+ batch: Batch
10
+ """Batched mesh of the chunk"""
11
+ nodes: set
12
+ """Set conaining references to all nodes in the chunk"""
13
+ static: bool
14
+ """Type of node that the chunk recognizes"""
15
+
16
+ def __init__(self, chunk_handler, position: tuple, static: bool, shader=None) -> None:
17
+ """
18
+ Basilisk chunk object.
19
+ Contains references to all nodes in the chunk.
20
+ Handles batching for its own nodes
21
+ """
22
+
23
+ # Back references
24
+ self.chunk_handler = chunk_handler
25
+
26
+ # Chunk Attrbiutes
27
+ self.position = position
28
+ self.static = static
29
+ self.shader = shader
30
+
31
+ # Create empty batch
32
+ self.batch = Batch(self)
33
+
34
+ # Create empty set for chunk's nodes
35
+ self.nodes = set()
36
+
37
+ def render(self) -> None:
38
+ """
39
+ Renders the chunk mesh
40
+ """
41
+
42
+ if self.batch.vao: self.batch.vao.render()
43
+
44
+ def update(self) -> bool:
45
+ """
46
+ Batches all the node meshes in the chunk
47
+ """
48
+
49
+ # Check if there are no nodes in the chunk
50
+ if not self.nodes: return False
51
+ # Batch the chunk nodes, return success bit
52
+ return self.batch.batch()
53
+
54
+ def node_update_callback(self, node):
55
+ if not self.batch.vbo: return
56
+
57
+ data = node.get_data()
58
+ self.batch.vbo.write(data, node.data_index * 25 * 4)
59
+
60
+ def add(self, node):
61
+ """
62
+ Adds an existing node to the chunk. Updates the node's chunk reference
63
+ """
64
+
65
+ self.nodes.add(node)
66
+ node.chunk = self
67
+
68
+ return node
69
+
70
+ def remove(self, node):
71
+ """
72
+ Removes a node from the chunk
73
+ """
74
+
75
+ if node == None: return
76
+
77
+ self.nodes.remove(node)
78
+ if self.batch and self.batch.vbo: self.batch.vbo.clear()
79
+
80
+ return node
81
+
82
+ def get_program(self):
83
+ """
84
+ Gets the program of the chunks nodes' shader
85
+ """
86
+
87
+ shader = self.shader
88
+
89
+ if shader: return shader.program
90
+ return self.chunk_handler.engine.shader.program
91
+
92
+ def __repr__(self) -> str:
93
+ return f'<Basilisk Chunk | {self.position}, {len(self.nodes)} nodes, {"static" if self.static else "dynamic"}>'
94
+
95
+ def __del__(self) -> None:
96
+ """
97
+ Deletes the batch if this chunk is deleted
98
+ """
99
+
100
100
  del self.batch