3 * ***** BEGIN GPL LICENSE BLOCK *****
5 * This program is free software; you can redistribute it and/or
6 * modify it under the terms of the GNU General Public License
7 * as published by the Free Software Foundation; either version 2
8 * of the License, or (at your option) any later version.
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software Foundation,
17 * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
19 * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV.
20 * All rights reserved.
22 * The Original Code is: all of this file.
24 * Contributor(s): none yet.
26 * ***** END GPL LICENSE BLOCK *****
29 #include "KX_SG_NodeRelationships.h"
36 * Implementation of classes defined in KX_SG_NodeRelationships.h
40 * first of all KX_NormalParentRelation
43 KX_NormalParentRelation *
44 KX_NormalParentRelation::
47 return new KX_NormalParentRelation();
51 KX_NormalParentRelation::
52 UpdateChildCoordinates(
54 const SG_Spatial * parent
56 MT_assert(child != NULL);
58 if (parent==NULL) { /* Simple case */
59 child->SetWorldFromLocalTransform();
63 // the childs world locations which we will update.
64 const MT_Vector3 & p_world_scale = parent->GetWorldScaling();
65 const MT_Point3 & p_world_pos = parent->GetWorldPosition();
66 const MT_Matrix3x3 & p_world_rotation = parent->GetWorldOrientation();
68 child->SetWorldScale(p_world_scale * child->GetLocalScale());
69 child->SetWorldOrientation(p_world_rotation * child->GetLocalOrientation());
70 child->SetWorldPosition(p_world_pos + p_world_scale * (p_world_rotation * child->GetLocalPosition()));
76 KX_NormalParentRelation::
79 return new KX_NormalParentRelation();
82 KX_NormalParentRelation::
83 ~KX_NormalParentRelation(
89 KX_NormalParentRelation::
90 KX_NormalParentRelation(
96 * Next KX_VertexParentRelation
100 KX_VertexParentRelation *
101 KX_VertexParentRelation::
104 return new KX_VertexParentRelation();
108 * Method inherited from KX_ParentRelation
112 KX_VertexParentRelation::
113 UpdateChildCoordinates(
115 const SG_Spatial * parent
118 MT_assert(child != NULL);
119 child->SetWorldScale(child->GetLocalScale());
122 child->SetWorldPosition(child->GetLocalPosition()+parent->GetWorldPosition());
124 child->SetWorldPosition(child->GetLocalPosition());
126 child->SetWorldOrientation(child->GetLocalOrientation());
127 return parent != NULL;
131 * Method inherited from KX_ParentRelation
135 KX_VertexParentRelation::
138 return new KX_VertexParentRelation();
141 KX_VertexParentRelation::
142 ~KX_VertexParentRelation(
148 KX_VertexParentRelation::
149 KX_VertexParentRelation(
156 * Slow parent relationship
159 KX_SlowParentRelation *
160 KX_SlowParentRelation::
164 return new KX_SlowParentRelation(relaxation);
168 * Method inherited from KX_ParentRelation
172 KX_SlowParentRelation::
173 UpdateChildCoordinates(
175 const SG_Spatial * parent
177 MT_assert(child != NULL);
179 const MT_Vector3 & child_scale = child->GetLocalScale();
180 const MT_Point3 & child_pos = child->GetLocalPosition();
181 const MT_Matrix3x3 & child_rotation = child->GetLocalOrientation();
183 // the childs world locations which we will update.
185 MT_Vector3 child_w_scale;
186 MT_Point3 child_w_pos;
187 MT_Matrix3x3 child_w_rotation;
191 // This is a slow parent relation
192 // first compute the normal child world coordinates.
194 MT_Vector3 child_n_scale;
195 MT_Point3 child_n_pos;
196 MT_Matrix3x3 child_n_rotation;
198 const MT_Vector3 & p_world_scale = parent->GetWorldScaling();
199 const MT_Point3 & p_world_pos = parent->GetWorldPosition();
200 const MT_Matrix3x3 & p_world_rotation = parent->GetWorldOrientation();
202 child_n_scale = p_world_scale * child_scale;
203 child_n_rotation = p_world_rotation * child_rotation;
205 child_n_pos = p_world_pos + p_world_scale *
206 (p_world_rotation * child_pos);
211 // get the current world positions
213 child_w_scale = child->GetWorldScaling();
214 child_w_pos = child->GetWorldPosition();
215 child_w_rotation = child->GetWorldOrientation();
217 // now 'interpolate' the normal coordinates with the last
218 // world coordinates to get the new world coordinates.
221 // The child world scale needs to be initialized in some way for this
224 // This is way of doing interpolation is nonsense
228 MT_Scalar weight = MT_Scalar(1)/(m_relax + 1);
229 for (i=0;i <3 ;i++) {
230 child_w_scale[i] = (m_relax * child_w_scale[i] + child_n_scale[i]) * weight;
231 child_w_pos[i] = (m_relax * child_w_pos[i] + child_n_pos[i]) * weight;
232 child_w_rotation[0][i] = (m_relax * child_w_rotation[0][i] + child_n_rotation[0][i]) * weight;
233 child_w_rotation[1][i] = (m_relax * child_w_rotation[1][i] + child_n_rotation[1][i]) * weight;
234 child_w_rotation[2][i] = (m_relax * child_w_rotation[2][i] + child_n_rotation[2][i]) * weight;
237 //FIXME: update physics controller.
239 child_w_scale = child_n_scale;
240 child_w_pos = child_n_pos;
241 child_w_rotation = child_n_rotation;
242 m_initialized = true;
247 child_w_scale = child_scale;
248 child_w_pos = child_pos;
249 child_w_rotation = child_rotation;
252 child->SetWorldScale(child_w_scale);
253 child->SetWorldPosition(child_w_pos);
254 child->SetWorldOrientation(child_w_rotation);
256 return parent != NULL;
260 * Method inherited from KX_ParentRelation
264 KX_SlowParentRelation::
267 return new KX_SlowParentRelation(m_relax);
270 KX_SlowParentRelation::
271 KX_SlowParentRelation(
280 KX_SlowParentRelation::
281 ~KX_SlowParentRelation(