From ce02dcad847ab934a9a13d38886edadf7de8db9e Mon Sep 17 00:00:00 2001 From: Adam Johnson Date: Tue, 23 Jun 2015 19:40:27 -0400 Subject: [PATCH] Fix missing colliders in PotS --- korman/exporter/physics.py | 67 ++++++++++++++++++++++---------------- korman/helpers.py | 16 +++++++++ 2 files changed, 55 insertions(+), 28 deletions(-) diff --git a/korman/exporter/physics.py b/korman/exporter/physics.py index fb153e5..851bf19 100644 --- a/korman/exporter/physics.py +++ b/korman/exporter/physics.py @@ -13,10 +13,12 @@ # You should have received a copy of the GNU General Public License # along with Korman. If not, see . +import bpy import mathutils from PyHSPlasma import * import weakref +from ..helpers import TemporaryObject from . import utils class PhysicsConverter: @@ -24,35 +26,44 @@ class PhysicsConverter: self._exporter = weakref.ref(exporter) def _convert_mesh_data(self, bo, physical, indices=True): - mesh = bo.data - mesh.update(calc_tessface=indices) - - # Yes, we have to have transform data here, even if we have a CoordInterface + mesh = bo.to_mesh(bpy.context.scene, True, "RENDER") mat = bo.matrix_world - physical.rot = utils.quaternion(mat.to_quaternion()) - physical.pos = utils.vector3(mat.to_translation()) - - # Physicals can't have scale... - scale = mat.to_scale() - if scale[0] == 1.0 and scale[1] == 1.0 and scale[2] == 1.0: - # Whew, don't need to do any math! - vertices = [hsVector3(i.co.x, i.co.y, i.co.z) for i in mesh.vertices] - else: - # Dagnabbit... - vertices = [hsVector3(i.co.x * scale.x, i.co.y * scale.y, i.co.z * scale.z) for i in mesh.vertices] - - if indices: - indices = [] - for face in mesh.tessfaces: - v = face.vertices - if len(v) == 3: - indices += v - elif len(v) == 4: - indices += (v[0], v[1], v[2],) - indices += (v[0], v[2], v[3],) - return (vertices, indices) - else: - return vertices + + with TemporaryObject(mesh, bpy.data.meshes.remove) as mesh: + # We can only use the plPhysical xforms if there is a CI... + if self._mgr.has_coordiface(bo): + mesh.update(calc_tessface=indices) + physical.pos = utils.vector3(mat.to_translation()) + quat = mat.to_quaternion() + quat.normalize() + physical.rot = utils.quaternion(quat) + + # Physicals can't have scale... + scale = mat.to_scale() + if scale[0] == 1.0 and scale[1] == 1.0 and scale[2] == 1.0: + # Whew, don't need to do any math! + vertices = [hsVector3(i.co.x, i.co.y, i.co.z) for i in mesh.vertices] + else: + # Dagnabbit... + vertices = [hsVector3(i.co.x * scale.x, i.co.y * scale.y, i.co.z * scale.z) for i in mesh.vertices] + else: + # apply the transform to the physical itself + mesh.transform(mat) + mesh.update(calc_tessface=indices) + vertices = [hsVector3(i.co.x, i.co.y, i.co.z) for i in mesh.vertices] + + if indices: + indices = [] + for face in mesh.tessfaces: + v = face.vertices + if len(v) == 3: + indices += v + elif len(v) == 4: + indices += (v[0], v[1], v[2],) + indices += (v[0], v[2], v[3],) + return (vertices, indices) + else: + return vertices def generate_physical(self, bo, so, name=None): """Generates a physical object for the given object pair""" diff --git a/korman/helpers.py b/korman/helpers.py index 7541a32..18c1aeb 100644 --- a/korman/helpers.py +++ b/korman/helpers.py @@ -32,6 +32,22 @@ class GoodNeighbor: setattr(cls, attr, value) bpy.context.scene.update() + +class TemporaryObject: + def __init__(self, obj, remove_func): + self._obj = obj + self._remove_func = remove_func + + def __enter__(self): + return self + + def __exit__(self, type, value, traceback): + self._remove_func(self._obj) + + def __getattr__(self, attr): + return getattr(self._obj, attr) + + def ensure_object_can_bake(bo, toggle): """Ensures that we can use Blender's baking operators on this object. Side effect: also ensures that the object will enter edit mode when requested."""