Skip to content

Commit 669adf0

Browse files
committed
BaseProject docstrings
1 parent fc1a20a commit 669adf0

File tree

1 file changed

+115
-26
lines changed

1 file changed

+115
-26
lines changed

demosys/project/base.py

+115-26
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,11 @@
1-
from demosys import context
2-
from demosys import resources
1+
from typing import Any, List, Type, Union
2+
3+
import moderngl
4+
from demosys import context, resources
5+
from demosys.effects import Effect
36
from demosys.effects.registry import effects
7+
from demosys.resources.meta import ResourceDescription
8+
from demosys.scene import Scene
49

510

611
class BaseProject:
@@ -16,37 +21,52 @@ def __init__(self):
1621
self._scenes = {}
1722
self._data = {}
1823

19-
def get_default_effect(self):
20-
raise NotImplementedError()
21-
2224
def create_effect_classes(self):
23-
"""Create effect classes in the registry"""
25+
"""
26+
Registers effect packages defined in ``effect_packages``.
27+
"""
2428
effects.polulate(self.effect_packages)
2529

26-
def create_external_resources(self):
30+
def create_external_resources(self) -> List[ResourceDescription]:
2731
"""
28-
Create resources defined externally such as resource modules in effect packages.
32+
Fetches all resource descriptions defined in effect packages.
2933
30-
:returns: List of resource descriptions to load
34+
Returns:
35+
List of resource descriptions to load
3136
"""
3237
return effects.get_effect_resources()
3338

34-
def create_resources(self):
39+
def create_resources(self) -> List[ResourceDescription]:
3540
"""
36-
Create resources for the project
41+
Create resources for the project.
42+
Simply returns the ``resources`` list and can be implemented to
43+
modify what a resource list is programmatically.
3744
38-
:returns: List of resource descriptions to load
45+
Returns:
46+
List of resource descriptions to load
3947
"""
4048
return self.resources
4149

4250
def create_effect_instances(self):
4351
"""
44-
Create instances of effects
52+
Create instances of effects.
53+
Must be implemented or ``NotImplementedError`` is raised.
4554
"""
4655
raise NotImplementedError()
4756

48-
def create_effect(self, label, name, *args, **kwargs):
49-
"""Create an effect instance"""
57+
def create_effect(self, label: str, name: str, *args, **kwargs) -> Effect:
58+
"""
59+
Create an effect instance adding it to the internal effects dictionary using the label as key.
60+
61+
Args:
62+
label (str): The unique label for the effect instance
63+
name (str): Name or full python path to the effect class we want to instantiate
64+
args: Positional arguments to the effect initializer
65+
kwargs: Keyword arguments to the effect initializer
66+
67+
Returns:
68+
The newly created Effect instance
69+
"""
5070
params = name.split('.')
5171
effect_cls = effects.find_effect_class(params[-1], package_name=".".join(params[:-1]))
5272
effect = effect_cls(*args, **kwargs)
@@ -61,12 +81,16 @@ def create_effect(self, label, name, *args, **kwargs):
6181

6282
def post_load(self):
6383
"""
64-
Actions after loading is complete
84+
Called after resources are loaded before effects starts rendering.
85+
It simply iterates each effect instance calling their ``post_load`` methods.
6586
"""
6687
for _, effect in self._effects.items():
6788
effect.post_load()
6889

6990
def load(self):
91+
"""
92+
Loads this project instance
93+
"""
7094
self.create_effect_classes()
7195

7296
self._add_resource_descriptions_to_pools(self.create_external_resources())
@@ -88,53 +112,118 @@ def load(self):
88112
self.post_load()
89113

90114
def _add_resource_descriptions_to_pools(self, meta_list):
115+
"""
116+
Takes a list of resource descriptions adding them
117+
to the resource pool they belong to scheduling them for loading.
118+
"""
91119
if not meta_list:
92120
return
93121

94122
for meta in meta_list:
95123
getattr(resources, meta.resource_type).add(meta)
96124

97125
def reload_programs(self):
126+
"""
127+
Reload all shader programs with the reloadable flag set
128+
"""
98129
print("Reloading programs:")
99130
for name, program in self._programs.items():
100131
if getattr(program, 'program', None):
101132
print(" - {}".format(program.meta.label))
102133
program.program = resources.programs.load(program.meta)
103134

104-
def get_effect(self, label):
135+
def get_effect(self, label: str) -> Effect:
136+
"""
137+
Get an effect instance by label
138+
139+
Args:
140+
label (str): The label for the effect instance
141+
142+
Returns:
143+
Effect class instance
144+
"""
105145
return self._get_resource(label, self._effects, "effect")
106146

107-
def get_effect_class(self, class_name, package_name=None):
147+
def get_effect_class(self, class_name, package_name=None) -> Type[Effect]:
148+
"""
149+
Get an effect class from the effect registry.
150+
151+
Args:
152+
class_name (str): The exact class name of the effect
153+
154+
Keyword Args:
155+
package_name (str): The python path to the effect package the effect name is located.
156+
This is optional and can be used to avoid issue with class name collisions.
157+
158+
Returns:
159+
Effect class
160+
"""
108161
return effects.find_effect_class(class_name, package_name=package_name)
109162

110-
def get_scene(self, label):
163+
def get_scene(self, label: str) -> Scene:
164+
"""
165+
Gets a scene by label
166+
167+
Args:
168+
label (str): The label for the scene to fetch
169+
170+
Returns:
171+
Scene instance
172+
"""
111173
return self._get_resource(label, self._scenes, "scene")
112174

113-
def get_program(self, label):
175+
def get_program(self, label: str) -> moderngl.Program:
114176
return self._get_resource(label, self._programs, "program")
115177

116-
def get_texture(self, label):
178+
def get_texture(self, label: str) -> Union[moderngl.Texture, moderngl.TextureArray,
179+
moderngl.Texture3D, moderngl.TextureCube]:
180+
"""
181+
Get a texture by label
182+
183+
Args:
184+
label (str): The label for the texture to fetch
185+
186+
Returns:
187+
Texture instance
188+
"""
117189
return self._get_resource(label, self._textures, "texture")
118190

119-
def get_data(self, label):
191+
def get_data(self, label: str) -> Any:
192+
"""
193+
Get a data resource by label
194+
195+
Args:
196+
label (str): The labvel for the data resource to fetch
197+
198+
Returns:
199+
The requeted data object
200+
"""
120201
return self._get_resource(label, self._data, "data")
121202

122-
def _get_resource(self, label, source, resource_type):
203+
def _get_resource(self, label: str, source: dict, resource_type: str):
204+
"""
205+
Generic resoure fetcher handling errors.
206+
207+
Args:
208+
label (str): The label to fetch
209+
source (dict): The dictionary to look up the label
210+
resource_type str: The display name of the resource type (used in errors)
211+
"""
123212
try:
124213
return source[label]
125214
except KeyError:
126215
raise ValueError("Cannot find {0} with label '{1}'.\nExisting {0} labels: {2}".format(
127216
resource_type, label, list(source.keys())))
128217

129-
def get_runnable_effects(self):
218+
def get_runnable_effects(self) -> List[Effect]:
130219
"""
131-
Returns all runnable effects in the project
220+
Returns all runnable effects in the project.
132221
133222
:return: List of all runnable effects
134223
"""
135224
return [effect for name, effect in self._effects.items() if effect.runnable]
136225

137226
@property
138-
def ctx(self):
227+
def ctx(self) -> moderngl.Context:
139228
"""The MondernGL context"""
140229
return context.ctx()

0 commit comments

Comments
 (0)