129 std::vector<KeyFrame>& keyFrames = transport->
keyFrames;
131 bool mapChange =
false;
132 for (
size_t i = 0; i < path.size(); ++i)
133 allPoints.push_back(G3D::Vector3(path[i]->Loc.X, path[i]->Loc.Y, path[i]->Loc.Z));
136 allPoints.insert(allPoints.begin(), allPoints.front().lerp(allPoints[1], -0.2f));
137 allPoints.push_back(allPoints.back().lerp(allPoints[allPoints.size() - 2], -0.2f));
138 allPoints.push_back(allPoints.back().lerp(allPoints[allPoints.size() - 2], -1.0f));
145 for (
size_t i = 0; i < path.size(); ++i)
150 if (i != path.size() - 1 && (node_i->
Flags & 1 || node_i->
ContinentID != path[i + 1]->ContinentID))
152 keyFrames.back().Teleport =
true;
162 keyFrames.push_back(k);
163 splinePath.push_back(G3D::Vector3(node_i->
Loc.
X, node_i->
Loc.
Y, node_i->
Loc.
Z));
171 if (splinePath.size() >= 2)
174 if (!keyFrames.front().IsStopFrame() && !keyFrames.front().Node->ArrivalEventID && !keyFrames.front().Node->DepartureEventID)
176 splinePath.erase(splinePath.begin());
177 keyFrames.erase(keyFrames.begin());
179 if (!keyFrames.back().IsStopFrame() && !keyFrames.back().Node->ArrivalEventID && !keyFrames.back().Node->DepartureEventID)
181 splinePath.pop_back();
182 keyFrames.pop_back();
186 ASSERT(!keyFrames.empty());
190 for (std::set<uint32>::const_iterator itr = transport->
mapsUsed.begin(); itr != transport->
mapsUsed.end(); ++itr)
199 keyFrames.back().Teleport =
true;
203 const float accel_dist = 0.5f * speed * speed / accel;
208 int32 firstStop = -1;
212 keyFrames[0].DistFromPrev = 0;
213 keyFrames[0].Index = 1;
214 if (keyFrames[0].IsStopFrame())
223 for (
size_t i = 1; i < keyFrames.size(); ++i)
225 if (keyFrames[i - 1].Teleport || i + 1 == keyFrames.size())
227 size_t extra = !keyFrames[i - 1].Teleport ? 1 : 0;
228 std::shared_ptr<TransportSpline> spline = std::make_shared<TransportSpline>();
230 spline->initLengths();
231 for (
size_t j = start; j < i + extra; ++j)
233 keyFrames[j].Index = j - start + 1;
234 keyFrames[j].DistFromPrev = float(spline->length(j - start, j + 1 - start));
236 keyFrames[j - 1].NextDistFromPrev = keyFrames[j].DistFromPrev;
237 keyFrames[j].Spline = spline;
240 if (keyFrames[i - 1].Teleport)
242 keyFrames[i].Index = i - start + 1;
243 keyFrames[i].DistFromPrev = 0.0f;
244 keyFrames[i - 1].NextDistFromPrev = 0.0f;
245 keyFrames[i].Spline = spline;
251 if (keyFrames[i].IsStopFrame())
260 keyFrames.back().NextDistFromPrev = keyFrames.front().DistFromPrev;
262 if (firstStop == -1 || lastStop == -1)
263 firstStop = lastStop = 0;
268 float tmpDist = 0.0f;
269 for (
size_t i = 0; i < keyFrames.size(); ++i)
271 int32 j = (i + lastStop) % keyFrames.size();
272 if (keyFrames[j].IsStopFrame() || j == lastStop)
275 tmpDist += keyFrames[j].DistFromPrev;
276 keyFrames[j].DistSinceStop = tmpDist;
280 for (
int32 i =
int32(keyFrames.size()) - 1; i >= 0; i--)
282 int32 j = (i + firstStop) % keyFrames.size();
283 tmpDist += keyFrames[(j + 1) % keyFrames.size()].DistFromPrev;
284 keyFrames[j].DistUntilStop = tmpDist;
285 if (keyFrames[j].IsStopFrame() || j == firstStop)
289 for (
size_t i = 0; i < keyFrames.size(); ++i)
291 float total_dist = keyFrames[i].DistSinceStop + keyFrames[i].DistUntilStop;
292 if (total_dist < 2 * accel_dist)
294 if (keyFrames[i].DistSinceStop < keyFrames[i].DistUntilStop)
297 float segment_time = 2.0f * std::sqrt((keyFrames[i].DistUntilStop + keyFrames[i].DistSinceStop) / accel);
299 keyFrames[i].TimeTo = segment_time - std::sqrt(2 * keyFrames[i].DistSinceStop / accel);
302 keyFrames[i].TimeTo = std::sqrt(2 * keyFrames[i].DistUntilStop / accel);
304 else if (keyFrames[i].DistSinceStop < accel_dist)
307 float segment_time = (keyFrames[i].DistUntilStop + keyFrames[i].DistSinceStop) / speed + (speed / accel);
309 keyFrames[i].TimeTo = segment_time - std::sqrt(2 * keyFrames[i].DistSinceStop / accel);
311 else if (keyFrames[i].DistUntilStop < accel_dist)
312 keyFrames[i].TimeTo = std::sqrt(2 * keyFrames[i].DistUntilStop / accel);
314 keyFrames[i].TimeTo = (keyFrames[i].DistUntilStop / speed) + (0.5f * speed / accel);
318 float segmentTime = 0.0f;
319 for (
size_t i = 0; i < keyFrames.size(); ++i)
321 int32 j = (i + lastStop) % keyFrames.size();
322 if (keyFrames[j].IsStopFrame() || j == lastStop)
323 segmentTime = keyFrames[j].TimeTo;
324 keyFrames[j].TimeFrom = segmentTime - keyFrames[j].TimeTo;
328 keyFrames[0].ArriveTime = 0;
329 float curPathTime = 0.0f;
330 if (keyFrames[0].IsStopFrame())
332 curPathTime = float(keyFrames[0].Node->Delay);
336 for (
size_t i = 1; i < keyFrames.size(); ++i)
338 curPathTime += keyFrames[i - 1].TimeTo;
339 if (keyFrames[i].IsStopFrame())
342 keyFrames[i - 1].NextArriveTime = keyFrames[i].ArriveTime;
343 curPathTime += float(keyFrames[i].Node->Delay);
348 curPathTime -= keyFrames[i].TimeTo;
350 keyFrames[i - 1].NextArriveTime = keyFrames[i].ArriveTime;
351 keyFrames[i].DepartureTime = keyFrames[i].ArriveTime;
355 keyFrames.back().NextArriveTime = keyFrames.back().DepartureTime;
357 transport->
pathTime = keyFrames.back().DepartureTime;