Source.Python icon indicating copy to clipboard operation
Source.Python copied to clipboard

An easy way to use dynamic_attributes with BaseEntity.

Open CookStar opened this issue 1 year ago • 0 comments

I don't know the current development status of Source.Python, so this is a brief note for all Source.Python users.

Currently server_classes/dynamic_attributes/properties/inputs/outputs/keyvalues/get_input/call_input is only available for Entity (only for networked entity), but they are actually useful for server-side BaseEntity as well.

This is a hack to access them with BaseEntity.

Code:

def set_base_entity_dynamic_attributes():
    # Source.Python Imports
    #   Core
    from core.cache import CachedProperty
    #   Entities
    from entities.entity import BaseEntity
    from entities.entity import Entity

    if not hasattr(BaseEntity, "__getattr__"):
        BaseEntity.__getattr__ = Entity.__getattr__

    if BaseEntity.__setattr__ != Entity.__setattr__:
        BaseEntity.__setattr__ = Entity.__setattr__

    if BaseEntity.__dir__ != Entity.__dir__:
        BaseEntity.__dir__ = Entity.__dir__

    if not hasattr(BaseEntity, "server_classes"):
        BaseEntity.server_classes = CachedProperty(Entity.server_classes.fget)
        BaseEntity.server_classes.__set_name__(BaseEntity, "server_classes")

    if not hasattr(BaseEntity, "dynamic_attributes"):
        BaseEntity.dynamic_attributes = CachedProperty(Entity.dynamic_attributes.fget)
        BaseEntity.dynamic_attributes.__set_name__(BaseEntity, "dynamic_attributes")

    if not hasattr(BaseEntity, "properties"):
        BaseEntity.properties = CachedProperty(Entity.properties.fget)
        BaseEntity.properties.__set_name__(BaseEntity, "properties")

    if not hasattr(BaseEntity, "inputs"):
        BaseEntity.inputs = CachedProperty(Entity.inputs.fget)
        BaseEntity.inputs.__set_name__(BaseEntity, "inputs")

    if not hasattr(BaseEntity, "outputs"):
        def outputs(self):
            """Iterate over all outputs available for the entity."""
            outputs = {}
            for server_class in self.server_classes:
                for output in server_class.outputs:
                    outputs[output] = self.get_output(output)
            return outputs

        BaseEntity.outputs = CachedProperty(outputs)
        BaseEntity.outputs.__set_name__(BaseEntity, "outputs")

    if not hasattr(BaseEntity, "keyvalues"):
        BaseEntity.keyvalues = CachedProperty(Entity.keyvalues.fget)
        BaseEntity.keyvalues.__set_name__(BaseEntity, "keyvalues")

    if not hasattr(BaseEntity, "get_input"):
        BaseEntity.get_input = Entity.get_input

    if not hasattr(BaseEntity, "call_input"):
        BaseEntity.call_input = Entity.call_input

set_base_entity_dynamic_attributes()

Demo:

# Source.Python Imports
#   Entities
from entities.entity import BaseEntity
base_entity = BaseEntity.find_or_create("logic_timer")
print(base_entity.refire_time)
base_entity.refire_time = 60
print(base_entity.refire_time)
base_entity.call_input("RefireTime", 30)
print(base_entity.refire_time)

CTimerEntity.ini

[keyvalue]

    refire_time = RefireTime

Output:

0.0
60.0
30.0

CookStar avatar Oct 02 '24 17:10 CookStar