예제 #1
0
    def __init__(self, temp_entity):
        """Initialize the instance.

        :param BaseTempEntity temp_entity:
            The base entity instance to copy the base from.
        """
        # Store the size of the temp entity...
        self._size = get_size(BaseTempEntity)

        # Get the aliases...
        self._aliases = GameConfigObj(SP_DATA_PATH / 'effects' /
                                      temp_entity.server_class.name + '.ini')

        # Get a dictionary to store the properties...
        self._properties = dict()

        # Add the properties to the dictionary...
        self._add_properties(temp_entity.server_class.table)

        # Loop through all properties...
        for prop in temp_entity.server_class.table:

            # Is the current prop a base class?
            if prop.name != 'baseclass':

                # Pass to the next property...
                continue

            # Add the current table to the properties...
            self._add_properties(prop.data_table)

        # Initialize the base class...
        super()._copy_base(temp_entity, self.size)
예제 #2
0
    def __init__(self, temp_entity):
        """Initialize the instance.

        :param BaseTempEntity temp_entity:
            The base entity instance to copy the base from.
        """
        # Store the size of the temp entity...
        self._size = get_size(BaseTempEntity)

        # Get the aliases...
        self._aliases = GameConfigObj(
            SP_DATA_PATH / 'effects' / temp_entity.server_class.name + '.ini')

        # Get a dictionary to store the properties...
        self._properties = dict()

        # Add the properties to the dictionary...
        self._add_properties(temp_entity.server_class.table)

        # Loop through all properties...
        for prop in temp_entity.server_class.table:

            # Is the current prop a base class?
            if prop.name != 'baseclass':

                # Pass to the next property...
                continue

            # Add the current table to the properties...
            self._add_properties(prop.data_table)

        # Initialize the base class...
        super()._copy_base(temp_entity, self.size)
예제 #3
0
 def _pre_user_message_begin(args):
     try:
         # Replace original recipients filter
         tmp_recipients = make_object(BaseRecipientFilter, args[1])
         _recipients.update(*tuple(tmp_recipients), clear=True)
     except RuntimeError:
         # Patch for issue #314
         tmp_recipients = RecipientFilter()
         (args[1] + 4).copy(
             get_object_pointer(tmp_recipients) + 4,
             get_size(RecipientFilter) - 4)
         _recipients.update(*tuple(tmp_recipients), clear=True)
     args[1] = _recipients
예제 #4
0
    def _pre_send_user_message(args):
        message_index = args[2]

        user_message_hooks = HookUserMessage.hooks[message_index]
        protobuf_user_message_hooks = HookProtobufUserMessage.hooks[
            message_index]

        # No need to do anything behind this if no listener is registered
        if not user_message_hooks and not protobuf_user_message_hooks:
            return

        try:
            # Replace original recipients filter
            tmp_recipients = make_object(BaseRecipientFilter, args[1])
            _recipients.update(*tuple(tmp_recipients), clear=True)
        except RuntimeError:
            # Patch for issue #314
            tmp_recipients = RecipientFilter()
            (args[1] + 4).copy(
                get_object_pointer(tmp_recipients) + 4,
                get_size(RecipientFilter) - 4)
            _recipients.update(*tuple(tmp_recipients), clear=True)
        args[1] = _recipients

        buffer = make_object(ProtobufMessage, args[3])

        protobuf_user_message_hooks.notify(_recipients, buffer)

        # No need to do anything behind this if no listener is registered
        if not user_message_hooks:
            return

        try:
            impl = get_user_message_impl(message_index)
        except NotImplementedError:
            return

        data = impl.read(buffer)
        user_message_hooks.notify(_recipients, data)

        # Update buffer if data has been changed
        if data.has_been_changed():
            buffer.clear()
            impl.write(buffer, data)
예제 #5
0
    def _get_type_size(type_name):
        """Helper method returning the size of the given type.

        :param str type_name: The name of the type.
        """
        # Is the type native?
        if Type.is_native(type_name):

            # Return the size of the type...
            return TYPE_SIZES[type_name.upper()]

        # Otherwise...
        else:

            # Get the size of the type...
            return get_size(manager.get_class(type_name))

        # Raise an exception...
        raise ValueError('"{}" is not a supported type.'.format(type_name))
예제 #6
0
    def _get_type_size(type_name):
        """Helper method returning the size of the given type.

        :param str type_name: The name of the type.
        """
        # Is the type native?
        if Type.is_native(type_name):

            # Return the size of the type...
            return TYPE_SIZES[type_name.upper()]

        # Otherwise...
        else:

            # Get the size of the type...
            return get_size(manager.get_class(type_name))

        # Raise an exception...
        raise ValueError('"{}" is not a supported type.'.format(type_name))
예제 #7
0
from entities.hooks import EntityCondition
#   Listeners
from listeners import on_player_run_command_listener_manager
from listeners import on_button_state_changed_listener_manager
#   Players
from players import UserCmd
from players.entity import Player
#   Memory
from memory import make_object
from memory import get_object_pointer
from memory import get_size

# =============================================================================
# >> CONSTANTS
# =============================================================================
USER_CMD_SIZE = get_size(UserCmd)


# =============================================================================
# >> CALLBACKS
# =============================================================================
@EntityPreHook(EntityCondition.is_player, 'run_command')
def _pre_player_run_command(args):
    if (not on_player_run_command_listener_manager
            and not on_button_state_changed_listener_manager):
        return

    player = make_object(Player, args[0])

    # https://github.com/Source-Python-Dev-Team/Source.Python/issues/149
    use_rtti_fix = SOURCE_ENGINE_BRANCH == 'tf2' and player.is_fake_client()
예제 #8
0
    def _set_property(self, prop_name, prop_type, value):
        """Set the given property to the given value.

        :param str prop_name: The name of the property.
        :param SendPropType prop_type: The type of the property.
        :param value object: To value to set to the given property.
        """
        # Is the given property not valid?
        if prop_name not in self.template.properties:

            # Raise an exception...
            raise NameError(
                '"{}" is not a valid property for temp entity "{}".'.format(
                    prop_name, self.name))

        # Get the property data...
        prop, offset, type_name = self.template.properties[prop_name]

        # Are the prop types matching?
        if prop.type != prop_type:

            # Raise an exception...
            raise TypeError('"{}" is not of type "{}".'.format(
                prop_name, prop_type))

        # Is the property an array?
        if prop_type == SendPropType.ARRAY:

            # Is the given value not an Array instance?
            if not isinstance(value, Array):

                # Raise an exception...
                raise TypeError('Given value is not an Array instance.')

            # Is the length not matching?
            if value._length != prop.length:

                # Raise an exception...
                raise ValueError('Given array is not of length "{}".'.format(
                    prop.length))

            # Copy the values...
            value.copy(get_object_pointer(self), self._get_type_size(
                type_name) * prop.length)

            # No need to go further...
            return

        # Otherwise, is the type native?
        elif Type.is_native(type_name):

            # Set the value of the property...
            getattr(get_object_pointer(self), 'set_{}'.format(type_name))(
                value, offset)

            # No need to go further...
            return

        # Otherwise...
        else:

            # Get the class...
            cls = manager.get_class(type_name)

            # Is the given value valid?
            if not isinstance(value, cls):

                # Raise an exception...
                raise TypeError('"{}" is not a valid "{}" value.'.format(
                    value, type_name))

            # Set the value of the property...
            get_object_pointer(value).copy(
                get_object_pointer(self) + offset, get_size(cls))

            # No need to go further...
            return

        # Raise an exception...
        raise NameError('Unable to set "{}" for the temp entity "{}".'.format(
            prop_name, self.name))
예제 #9
0
#   Listeners
from listeners import on_player_run_command_listener_manager
from listeners import on_button_state_changed_listener_manager
#   Players
from players import UserCmd
from players.entity import Player
#   Memory
from memory import make_object
from memory import get_object_pointer
from memory import get_size


# =============================================================================
# >> CONSTANTS
# =============================================================================
USER_CMD_SIZE = get_size(UserCmd)


# =============================================================================
# >> CALLBACKS
# =============================================================================
@EntityPreHook(EntityCondition.is_player, 'run_command')
def _pre_player_run_command(args):
    if (not on_player_run_command_listener_manager
            and not on_button_state_changed_listener_manager):
        return

    player = make_object(Player, args[0])

    # https://github.com/Source-Python-Dev-Team/Source.Python/issues/149
    use_rtti_fix = SOURCE_ENGINE_BRANCH == 'tf2' and player.is_fake_client()
예제 #10
0
    def _set_property(self, prop_name, prop_type, value):
        """Set the given property to the given value.

        :param str prop_name: The name of the property.
        :param SendPropType prop_type: The type of the property.
        :param value object: To value to set to the given property.
        """
        # Is the given property not valid?
        if prop_name not in self.template.properties:

            # Raise an exception...
            raise NameError(
                '"{}" is not a valid property for temp entity "{}".'.format(
                    prop_name, self.name))

        # Get the property data...
        prop, offset, type_name = self.template.properties[prop_name]

        # Are the prop types matching?
        if prop.type != prop_type:

            # Raise an exception...
            raise TypeError('"{}" is not of type "{}".'.format(
                prop_name, prop_type))

        # Is the property an array?
        if prop_type == SendPropType.ARRAY:

            # Is the given value not an Array instance?
            if not isinstance(value, Array):

                # Raise an exception...
                raise TypeError('Given value is not an Array instance.')

            # Is the length not matching?
            if value._length != prop.length:

                # Raise an exception...
                raise ValueError('Given array is not of length "{}".'.format(
                    prop.length))

            # Copy the values...
            value.copy(get_object_pointer(self),
                       self._get_type_size(type_name) * prop.length)

            # No need to go further...
            return

        # Otherwise, is the type native?
        elif Type.is_native(type_name):

            # Set the value of the property...
            getattr(get_object_pointer(self),
                    'set_{}'.format(type_name))(value, offset)

            # No need to go further...
            return

        # Otherwise...
        else:

            # Get the class...
            cls = manager.get_class(type_name)

            # Is the given value valid?
            if not isinstance(value, cls):

                # Raise an exception...
                raise TypeError('"{}" is not a valid "{}" value.'.format(
                    value, type_name))

            # Set the value of the property...
            get_object_pointer(value).copy(
                get_object_pointer(self) + offset, get_size(cls))

            # No need to go further...
            return

        # Raise an exception...
        raise NameError('Unable to set "{}" for the temp entity "{}".'.format(
            prop_name, self.name))