diff options
Diffstat (limited to 'source/gameengine/Ketsji/KX_SG_NodeRelationships.cpp')
-rw-r--r-- | source/gameengine/Ketsji/KX_SG_NodeRelationships.cpp | 328 |
1 files changed, 328 insertions, 0 deletions
diff --git a/source/gameengine/Ketsji/KX_SG_NodeRelationships.cpp b/source/gameengine/Ketsji/KX_SG_NodeRelationships.cpp new file mode 100644 index 00000000000..16529a91471 --- /dev/null +++ b/source/gameengine/Ketsji/KX_SG_NodeRelationships.cpp @@ -0,0 +1,328 @@ +/** + * $Id$ + * ***** BEGIN GPL/BL DUAL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. The Blender + * Foundation also sells licenses for use in proprietary software under + * the Blender License. See http://www.blender.org/BL/ for information + * about this. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL/BL DUAL LICENSE BLOCK ***** + */ + +#include "KX_SG_NodeRelationships.h" + + +/** + * Implementation of classes defined in KX_SG_NodeRelationships.h + */ + +/** + * first of all KX_NormalParentRelation + */ + + KX_NormalParentRelation * +KX_NormalParentRelation:: +New( +) { + return new KX_NormalParentRelation(); +} + + void +KX_NormalParentRelation:: +UpdateChildCoordinates( + SG_Spatial * child, + const SG_Spatial * parent +){ + assert(child != NULL); + + // This way of accessing child coordinates is a bit cumbersome + // be nice to have non constant reference access to these values. + + const MT_Vector3 & child_scale = child->GetLocalScale(); + const MT_Point3 & child_pos = child->GetLocalPosition(); + const MT_Matrix3x3 & child_rotation = child->GetLocalOrientation(); + + // the childs world locations which we will update. + + MT_Vector3 child_w_scale; + MT_Point3 child_w_pos; + MT_Matrix3x3 child_w_rotation; + + if (parent) { + + const MT_Vector3 & p_world_scale = parent->GetWorldScaling(); + const MT_Point3 & p_world_pos = parent->GetWorldPosition(); + const MT_Matrix3x3 & p_world_rotation = parent->GetWorldOrientation(); + + child_w_scale = p_world_scale * child_scale; + child_w_rotation = p_world_rotation * child_rotation; + + child_w_pos = p_world_pos + p_world_scale * + (p_world_rotation * child_pos); + } else { + + child_w_scale = child_scale; + child_w_pos = child_pos; + child_w_rotation = child_rotation; + } + + child->SetWorldScale(child_w_scale); + child->SetWorldPosition(child_w_pos); + child->SetWorldOrientation(child_w_rotation); +} + + SG_ParentRelation * +KX_NormalParentRelation:: +NewCopy( +){ + return new KX_NormalParentRelation(); +} + +KX_NormalParentRelation:: +~KX_NormalParentRelation( +){ + //nothing to do +} + + +KX_NormalParentRelation:: +KX_NormalParentRelation( +){ + // nothing to do +} + +/** + * Next KX_VertexParentRelation + */ + + + KX_VertexParentRelation * +KX_VertexParentRelation:: +New( +){ + return new KX_VertexParentRelation(); +} + +/** + * Method inherited from KX_ParentRelation + */ + + void +KX_VertexParentRelation:: +UpdateChildCoordinates( + SG_Spatial * child, + const SG_Spatial * parent +){ + + assert(child != NULL); + + const MT_Vector3 & child_scale = child->GetLocalScale(); + const MT_Point3 & child_pos = child->GetLocalPosition(); + const MT_Matrix3x3 & child_rotation = child->GetLocalOrientation(); + + // the childs world locations which we will update. + + MT_Vector3 child_w_scale; + MT_Point3 child_w_pos; + MT_Matrix3x3 child_w_rotation; + + if (parent) { + + // This is a vertex parent so we do not inherit orientation + // information. + + const MT_Vector3 & p_world_scale = parent->GetWorldScaling(); + const MT_Point3 & p_world_pos = parent->GetWorldPosition(); + const MT_Matrix3x3 & p_world_rotation = parent->GetWorldOrientation(); + + child_w_scale = child_scale; + child_w_rotation = child_rotation; + child_w_pos = p_world_pos + child_pos; + + } else { + + child_w_scale = child_scale; + child_w_pos = child_pos; + child_w_rotation = child_rotation; + } + + child->SetWorldScale(child_w_scale); + child->SetWorldPosition(child_w_pos); + child->SetWorldOrientation(child_w_rotation); +} + +/** + * Method inherited from KX_ParentRelation + */ + + SG_ParentRelation * +KX_VertexParentRelation:: +NewCopy( +){ + return new KX_VertexParentRelation(); +}; + +KX_VertexParentRelation:: +~KX_VertexParentRelation( +){ + //nothing to do +} + + +KX_VertexParentRelation:: +KX_VertexParentRelation( +){ + //nothing to do +} + + +/** + * Slow parent relationship + */ + + KX_SlowParentRelation * +KX_SlowParentRelation:: +New( + MT_Scalar relaxation +){ + return new KX_SlowParentRelation(relaxation); +} + +/** + * Method inherited from KX_ParentRelation + */ + + void +KX_SlowParentRelation:: +UpdateChildCoordinates( + SG_Spatial * child, + const SG_Spatial * parent +){ + assert(child != NULL); + + const MT_Vector3 & child_scale = child->GetLocalScale(); + const MT_Point3 & child_pos = child->GetLocalPosition(); + const MT_Matrix3x3 & child_rotation = child->GetLocalOrientation(); + + // the childs world locations which we will update. + + MT_Vector3 child_w_scale; + MT_Point3 child_w_pos; + MT_Matrix3x3 child_w_rotation; + + if (parent) { + + // This is a slow parent relation + // first compute the normal child world coordinates. + + MT_Vector3 child_n_scale; + MT_Point3 child_n_pos; + MT_Matrix3x3 child_n_rotation; + + const MT_Vector3 & p_world_scale = parent->GetWorldScaling(); + const MT_Point3 & p_world_pos = parent->GetWorldPosition(); + const MT_Matrix3x3 & p_world_rotation = parent->GetWorldOrientation(); + + child_n_scale = p_world_scale * child_scale; + child_n_rotation = p_world_rotation * child_rotation; + + child_n_pos = p_world_pos + p_world_scale * + (p_world_rotation * child_pos); + + + if (m_initialized) { + + // get the current world positions + + child_w_scale = child->GetWorldScaling(); + child_w_pos = child->GetWorldPosition(); + child_w_rotation = child->GetWorldOrientation(); + + // now 'interpolate' the normal coordinates with the last + // world coordinates to get the new world coordinates. + + // problem 1: + // The child world scale needs to be initialized in some way for this + // to make sense + // problem 2: + // This is way of doing interpolation is nonsense + + int i; + + MT_Scalar weight = MT_Scalar(1)/(m_relax + 1); + for (i=0;i <3 ;i++) { + child_w_scale[i] = (m_relax * child_w_scale[i] + child_n_scale[i]) * weight; + child_w_pos[i] = (m_relax * child_w_pos[i] + child_n_pos[i]) * weight; + child_w_rotation[0][i] = (m_relax * child_w_rotation[0][i] + child_n_rotation[0][i]) * weight; + child_w_rotation[1][i] = (m_relax * child_w_rotation[1][i] + child_n_rotation[1][i]) * weight; + child_w_rotation[2][i] = (m_relax * child_w_rotation[2][i] + child_n_rotation[2][i]) * weight; + } + } else { + child_w_scale = child_n_scale; + child_w_pos = child_n_pos; + child_w_rotation = child_n_rotation; + m_initialized = true; + } + + } else { + + child_w_scale = child_scale; + child_w_pos = child_pos; + child_w_rotation = child_rotation; + } + + child->SetWorldScale(child_w_scale); + child->SetWorldPosition(child_w_pos); + child->SetWorldOrientation(child_w_rotation); +} + +/** + * Method inherited from KX_ParentRelation + */ + + SG_ParentRelation * +KX_SlowParentRelation:: +NewCopy( +){ + return new KX_SlowParentRelation(m_relax); +} + +KX_SlowParentRelation:: +KX_SlowParentRelation( + MT_Scalar relaxation +): + m_relax(relaxation), + m_initialized(false) +{ + //nothing to do +} + +KX_SlowParentRelation:: +~KX_SlowParentRelation( +){ + //nothing to do +} + + + + |