hugoruscitti/pilas

View on GitHub
pilasengine/fisica/figura.py

Summary

Maintainability
C
1 day
Test Coverage
# -*- encoding: utf-8 -*-
# pilas engine: un motor para hacer videojuegos
#
# Copyright 2010-2014 - Hugo Ruscitti
# License: LGPLv3 (see http://www.gnu.org/licenses/lgpl.html)
#
# Website - http://www.pilas-engine.com.ar

import math
from pilasengine import utils
from pilasengine import etiquetas

class Figura(object):
    """Representa un figura que simula un cuerpo fisico.

    Esta figura es abstracta, no está pensada para crear
    objetos a partir de ella. Se usa como base para el resto
    de las figuras cómo el Circulo o el Rectangulo simplemente."""

    def __init__(self, fisica, pilas):
        self.fisica = fisica
        self.pilas = pilas
        self.id = pilas.utils.obtener_uuid()
        self._dinamica = True
        self.figuras_en_contacto = []
        self.etiquetas = etiquetas.Etiquetas()
        self.etiquetas.agregar(self.__class__.__name__)
        self._vivo = True
        self.z = 0

    def obtener_x(self):
        "Retorna la posición horizontal del cuerpo."
        return utils.convertir_a_pixels(self._cuerpo.position.x)

    def definir_x(self, x):
        """Define la posición horizontal del cuerpo.

        :param x: El valor horizontal a definir.
        """
        self._cuerpo.position = utils.convertir_a_metros(x), self._cuerpo.position.y

    def obtener_y(self):
        "Retorna la posición vertical del cuerpo."
        return utils.convertir_a_pixels(self._cuerpo.position.y)

    def definir_y(self, y):
        """Define la posición vertical del cuerpo.

        :param y: El valor vertical a definir.
        """
        self._cuerpo.position = self._cuerpo.position.x, utils.convertir_a_metros(y)

    def definir_posicion(self, x, y):
        """Define la posición para el cuerpo.

        :param x: Posición horizontal que se asignará al cuerpo.
        :param y: Posición vertical que se asignará al cuerpo.
        """
        self.definir_x(x)
        self.definir_y(y)

    def obtener_rotacion(self):
        return math.degrees(self._cuerpo.angle)

    def definir_rotacion(self, angulo):
        # TODO: simplificar a la nueva api.
        self._cuerpo.angle = math.radians(angulo)

    def set_x(self, x):
        self.definir_x(x)

    def get_x(self):
        return self.obtener_x()

    def set_y(self, y):
        self.definir_y(y)

    def get_y(self):
        return self.obtener_y()

    def set_rotation(self, angulo):
        self.definir_rotacion(angulo)

    def get_rotation(self):
        return self.obtener_rotacion()

    def impulsar(self, dx, dy):
        # TODO: convertir los valores dx y dy a metros.
        try:
            self._cuerpo.ApplyLinearImpulse((dx, dy), (0, 0))
        except TypeError, e:
            self._cuerpo.ApplyLinearImpulse((dx, dy), (0, 0), True)

    def obtener_velocidad_lineal(self):
        # TODO: convertir a pixels
        velocidad = self._cuerpo.linearVelocity
        return (velocidad.x, velocidad.y)

    def detener(self):
        """Hace que la figura regrese al reposo."""
        self.definir_velocidad_lineal(0, 0)

    def definir_velocidad_lineal(self, dx=None, dy=None):
        # TODO: convertir a metros
        anterior_dx, anterior_dy = self.obtener_velocidad_lineal()

        if dx is None:
            dx = anterior_dx
        if dy is None:
            dy = anterior_dy

        b2vec = self._cuerpo.linearVelocity
        b2vec.x = dx
        b2vec.y = dy

        # Añadimos el try, porque aparece el siguiente error:
        # TypeError: in method 'b2Vec2___call__', argument 2 of type 'int32'
        try:
            self._cuerpo.linearVelocity(b2vec)
        except:
            pass

    def empujar(self, dx=None, dy=None):
        # TODO: convertir a metros???
        self.definir_velocidad_lineal(dx, dy)

    def get_velocidad_x(self):
        dx, _ = self.obtener_velocidad_lineal()
        return dx

    def set_velocidad_x(self, dx):
        dy = self.velocidad_y
        self.definir_velocidad_lineal(dx, dy)

    def get_velocidad_y(self):
        _, dy = self.obtener_velocidad_lineal()
        return dy

    def set_velocidad_y(self, dy):
        dx = self.velocidad_x
        self.definir_velocidad_lineal(dx, dy)

    def eliminar(self):
        """Quita una figura de la simulación."""
        if self._vivo:
            self.fisica.eliminar_figura(self._cuerpo)
            self._vivo = False

    def esta_eliminado(self):
        return not self._vivo

    def obtener_sensor(self):
        return self._sensor

    def definir_sensor(self, s):
        self._sensor = s
        #self._cuerpo.fixtures[0].sensor = s

        if s:
            self._cuerpo.gravityScale = 0
            self._cuerpo.fixtures[0].userData['sensor'] = True
        else:
            self._cuerpo.gravityScale = 1.0
            self._cuerpo.fixtures[0].userData['sensor'] = False


    def obtener_colision(self):
        return self._actor_que_representa_como_area_de_colision

    def definir_colision(self, actor):
        self._actor_que_representa_como_area_de_colision = actor
        self._cuerpo.fixtures[0].userData['actor'] = actor

    def obtener_escala_de_gravedad(self):
        return self._cuerpo.gravityScale

    def definir_escala_de_gravedad(self, s):
        self._cuerpo.gravityScale = s

    def obtener_dinamica(self):
        return self._dinamica

    def definir_dinamica(self, d):
        self._dinamica = d

        if d:
            self.escala_de_gravedad = 1
            self._cuerpo.fixtures[0].userData['dinamica'] = True
            self._cuerpo.fixedRotation = False
        else:
            self.escala_de_gravedad = 0
            self._cuerpo.fixtures[0].userData['dinamica'] = False
            self._cuerpo.fixedRotation = True

    def obtener_sin_rotacion(self):
        return self._cuerpo.fixedRotation

    def definir_sin_rotacion(self, rotacion):
        self._cuerpo.fixedRotation = rotacion

    def __repr__(self):
        return "<Figura %s en (%d, %d)>" % (self.__class__.__name__, self.x, self.y)

    x = property(get_x, set_x, doc="define la posición horizontal.")
    y = property(get_y, set_y, doc="define la posición vertical.")
    rotacion = property(get_rotation, set_rotation, doc="define la rotacion.")
    sensor = property(obtener_sensor, definir_sensor)
    actor_que_representa_como_area_de_colision = property(obtener_colision, definir_colision)
    escala_de_gravedad = property(obtener_escala_de_gravedad, definir_escala_de_gravedad)
    dinamica = property(obtener_dinamica, definir_dinamica)
    sin_rotacion = property(obtener_sin_rotacion, definir_sin_rotacion)

    velocidad_x = property(get_velocidad_x, set_velocidad_x, doc="define la velocidad horizontal.")
    velocidad_y = property(get_velocidad_y, set_velocidad_y, doc="define la velocidad vertical.")