Free Electron
LocatorFromPointsSystem.h
Go to the documentation of this file.
1 /* Copyright (C) 2003-2021 Free Electron Organization
2  Any use of this software requires a license. If a valid license
3  was not distributed with this file, visit freeelectron.org. */
4 
5 /** @file */
6 
7 #ifndef __tire_LocatorFromPointsSystem_h__
8 #define __tire_LocatorFromPointsSystem_h__
9 
10 #include "solve/solve.h"
11 
12 namespace fe
13 {
14 namespace ext
15 {
16 
17 class LocatorFromPointsSystem :
18  virtual public Stepper,
19  public Initialize<LocatorFromPointsSystem>
20 {
21  public:
22  struct Item
23  {
24  WeakRecord m_r_parent;
25  WeakRecord m_r_p0;
26  WeakRecord m_r_p1;
27  WeakRecord m_r_p2;
28  t_moa_xform m_inv_R;
29  bool m_has_force;
30  };
31  LocatorFromPointsSystem(void) { }
32  void initialize(void) {}
33 virtual void compile(const t_note_id &a_note_id)
34  {
35  sp<Scope> spScope = m_rg_dataset->scope();
36 
37  if(!spScope.isValid()) { return; }
38 
39  enforce<AsTire,AsTireLive>(m_rg_dataset);
40 
41  m_asPoint.bind(spScope);
42  m_asForcePoint.bind(spScope);
43  m_asLocatorFromPoints.bind(spScope);
44  m_asForcePoints.bind(spScope);
45 
46  std::vector<Record> candidates;
47  m_asLocatorFromPoints.filter(candidates, m_rg_dataset);
48 
49  for(unsigned int i_candidate = 0; i_candidate < candidates.size();
50  i_candidate++)
51  {
52  Record &r_candidate = candidates[i_candidate];
53  Item item;
54  item.m_r_parent = r_candidate;
55  item.m_r_p0 = m_asLocatorFromPoints.p0(r_candidate);
56  item.m_r_p1 = m_asLocatorFromPoints.p1(r_candidate);
57  item.m_r_p2 = m_asLocatorFromPoints.p2(r_candidate);
58  if( item.m_r_p0.isValid() &&
59  item.m_r_p1.isValid() &&
60  item.m_r_p2.isValid() &&
61  m_asPoint.check(item.m_r_p0) &&
62  m_asPoint.check(item.m_r_p1) &&
63  m_asPoint.check(item.m_r_p2) )
64  {
65 
66  t_moa_xform frame;
67  t_moa_xform relative;
68  setIdentity(relative);
69 
70  bool frame_made = makeFrame(frame,
71  m_asPoint.location(item.m_r_p0),
72  m_asPoint.location(item.m_r_p1),
73  m_asPoint.location(item.m_r_p2),
74  relative);
75 
76  invert(item.m_inv_R, frame);
77 
78  relative = m_asLocatorFromPoints.transform(r_candidate);
79 
80  item.m_inv_R = relative * item.m_inv_R;
81 
82  if(m_asForcePoints.check(r_candidate)
83  && m_asForcePoint.check(item.m_r_p0)
84  && m_asForcePoint.check(item.m_r_p1)
85  && m_asForcePoint.check(item.m_r_p2))
86  {
87  item.m_has_force = true;
88  }
89  else
90  {
91  item.m_has_force = false;
92  }
93 
94  m_items.push_back(item);
95  }
96  }
97  }
98  void step(t_moa_real a_dt)
99  {
100  for(unsigned int i_item = 0; i_item < m_items.size(); i_item++)
101  {
102  WeakRecord &r_p0 = m_items[i_item].m_r_p0;
103  WeakRecord &r_p1 = m_items[i_item].m_r_p1;
104  WeakRecord &r_p2 = m_items[i_item].m_r_p2;
105  WeakRecord &r_item = m_items[i_item].m_r_parent;
106 
107  t_moa_xform frame;
108  t_moa_xform relative;
109  setIdentity(relative);
110  bool frame_made = makeFrame(frame,
111  m_asPoint.location(r_p0),
112  m_asPoint.location(r_p1),
113  m_asPoint.location(r_p2),
114  m_items[i_item].m_inv_R);
115 
116  m_asLocatorFromPoints.transform(r_item) = frame;
117 
118  if(m_items[i_item].m_has_force)
119  {
120  // p0 is the "reference root, so we'll use that velocity
121  t_moa_xform inv_frame;
122  invert(inv_frame, frame);
123  t_moa_v3 p0_v = rotateVector<3, t_moa_real>
124  (inv_frame, m_asForcePoint.velocity(r_p0));
125 
126  m_asForcePoints.velocity(r_item) = p0_v;
127  }
128 //TODO: ang vel -- frame ang is purely reflection -- useful ang vel from driveline
129 //TODO: grip point TM
130  }
131 
132  //TODO: not sure accumulate should not be its own note
133 //the problem here is that step is "outbound" mutation, and accumulate
134 //is "inbound" mutation, so what happens out-there should happen in between, to optimize
135 //fidelity per step size
136  accumulate();
137  }
138  void accumulate(void)
139  {
140  for(unsigned int i_item = 0; i_item < m_items.size(); i_item++)
141  {
142  if(!m_items[i_item].m_has_force) { continue; }
143 
144  WeakRecord &r_p0 = m_items[i_item].m_r_p0;
145  WeakRecord &r_p1 = m_items[i_item].m_r_p1;
146  WeakRecord &r_p2 = m_items[i_item].m_r_p2;
147  WeakRecord &r_item = m_items[i_item].m_r_parent;
148 
149  t_moa_xform xform = m_asLocatorFromPoints.transform(r_item);
150 
151  t_moa_v3 F = rotateVector<3, t_moa_real>
152  (xform, m_asForcePoints.force(r_item));
153  t_moa_v3 M = rotateVector<3, t_moa_real>
154  (xform, m_asForcePoints.moment(r_item));
155 
156  t_moa_v3 P = xform.translation();
157 
158  applyFMToPoints(F, M, P, m_asForcePoint, r_p0, r_p1, r_p2);
159 
160 #if 0
161  t_moa_v3 A = m_asPoint.location(r_p0) - P;
162 
163  M[0] += - F[2] * A[1] + F[1] * A[2];
164  M[1] += F[2] * A[0] - F[0] * A[2];
165  M[2] += - F[1] * A[0] + F[0] * A[1];
166 
167  m_asForcePoint.force(r_p0) += F;
168 
169  t_moa_v3 p0 = m_asPoint.location(r_p0);
170  t_moa_v3 p1 = m_asPoint.location(r_p1);
171  t_moa_v3 p2 = m_asPoint.location(r_p2);
172 
173  t_moa_v3 F0(0.0,0.0,0.0);
174  t_moa_v3 F1(0.0,0.0,0.0);
175  t_moa_v3 F2(0.0,0.0,0.0);
176 
177  t_moa_xform frame;
178  t_moa_xform relative;
179  setIdentity(relative);
180  bool frame_made = makeFrame(frame,
181  p0,
182  p1,
183  p2,
184  relative);
185 
186  t_moa_xform frame_inv;
187  invert(frame_inv, frame);
188  t_moa_v3 r0 = transformVector<3, t_moa_real>(frame_inv, p0);
189  t_moa_v3 r1 = transformVector<3, t_moa_real>(frame_inv, p1);
190  t_moa_v3 r2 = transformVector<3, t_moa_real>(frame_inv, p2);
191  t_moa_v3 frameM = rotateVector<3, t_moa_real>(frame_inv,M);
192 
193  // M0
194  t_moa_real arm = r2[2];
195  F2[1] -= frameM[0] / arm;
196  F0[1] += frameM[0] / arm;
197  t_moa_real residue = (frameM[0] / arm) * r2[0];
198  arm = r1[0];
199  F1[1] += residue / arm;
200  F0[1] -= residue / arm;
201 
202  // M1
203  arm = r1[0];
204  F1[2] -= frameM[1] / arm;
205  F0[2] += frameM[1] / arm;
206 
207  // M2
208  arm = r1[0];
209  F1[1] += frameM[2] / arm;
210  F0[1] -= frameM[2] / arm;
211 
212  F0 = rotateVector<3, t_moa_real>(frame, F0);
213  F1 = rotateVector<3, t_moa_real>(frame, F1);
214  F2 = rotateVector<3, t_moa_real>(frame, F2);
215 
216  m_asForcePoint.force(r_p0) += F0;
217  m_asForcePoint.force(r_p1) += F1;
218  m_asForcePoint.force(r_p2) += F2;
219 #endif
220  }
221  }
222 
223  std::vector<Item> m_items;
224  AsPoint m_asPoint;
225  AsForcePoint m_asForcePoint;
226  AsLocatorFromPoints m_asLocatorFromPoints;
227  AsForceLocator m_asForcePoints;
228 };
229 
230 } /* namespace ext */
231 } /* namespace fe */
232 
233 #endif /* __tire_LocatorFromPointsSystem_h__ */
234 
kernel
Definition: namespace.dox:3
Matrix< 4, 4, T > & invert(Matrix< 4, 4, T > &a_inverted, const Matrix< 4, 4, T > &a_matrix)
4x4 full matrix inversion
Definition: Matrix.h:1033