RigsofRods
Soft-body Physics Simulation
Savegame.cpp
Go to the documentation of this file.
1 /*
2  This source file is part of Rigs of Rods
3  Copyright 2005-2012 Pierre-Michel Ricordel
4  Copyright 2007-2012 Thomas Fischer
5  Copyright 2013-2020 Petr Ohlidal
6 
7  For more information, see http://www.rigsofrods.org/
8 
9  Rigs of Rods is free software: you can redistribute it and/or modify
10  it under the terms of the GNU General Public License version 3, as
11  published by the Free Software Foundation.
12 
13  Rigs of Rods is distributed in the hope that it will be useful,
14  but WITHOUT ANY WARRANTY; without even the implied warranty of
15  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16  GNU General Public License for more details.
17 
18  You should have received a copy of the GNU General Public License
19  along with Rigs of Rods. If not, see <http://www.gnu.org/licenses/>.
20 */
21 
22 #include "Application.h"
23 
24 #include "AeroEngine.h"
25 #include "Application.h"
26 #include "Actor.h"
27 #include "Buoyance.h"
28 #include "CacheSystem.h"
29 #include "ContentManager.h"
30 #include "Console.h"
31 #include "EngineSim.h"
32 #include "GameContext.h"
33 #include "GUIManager.h"
34 #include "GUI_MessageBox.h"
35 #include "InputEngine.h"
36 #include "Language.h"
37 #include "PlatformUtils.h"
38 #include "ScrewProp.h"
39 #include "Skidmark.h"
40 #include "SkyManager.h"
41 #include "Terrain.h"
42 #include "TuneupFileFormat.h"
43 
44 #include <rapidjson/rapidjson.h>
45 #include <fstream>
46 
47 #define SAVEGAME_FILE_FORMAT 3
48 
49 using namespace Ogre;
50 using namespace RoR;
51 
52 // --------------------------------
53 // GameContext functions
54 
55 std::string GameContext::GetQuicksaveFilename()
56 {
57  std::string terrain_name = App::sim_terrain_name->getStr();
58  std::string mp = (App::mp_state->getEnum<MpState>() == RoR::MpState::CONNECTED) ? "_mp" : "";
59 
60  return "quicksave_" + StringUtil::replaceAll(terrain_name, ".terrn2", "") + mp + ".sav";
61 }
62 
63 void GameContext::LoadScene(std::string const& filename)
64 {
65  ROR_ASSERT(App::GetGameContext()->GetTerrain());
66  m_actor_manager.LoadScene(filename);
67 }
68 
69 void GameContext::SaveScene(std::string const& filename)
70 {
71  m_actor_manager.SaveScene(filename);
72 }
73 
74 std::string GameContext::ExtractSceneName(std::string const& filename)
75 {
76  // Read from disk
77  rapidjson::Document j_doc;
78  if (!App::GetContentManager()->LoadAndParseJson(filename, RGN_SAVEGAMES, j_doc) ||
79  !j_doc.IsObject() || !j_doc.HasMember("format_version") || !j_doc["format_version"].IsNumber() ||
80  !j_doc.HasMember("scene_name") || !j_doc["scene_name"].IsString())
81  return "";
82 
83  return j_doc["scene_name"].GetString();
84 }
85 
86 std::string GameContext::ExtractSceneTerrain(std::string const& filename)
87 {
88  // Read from disk
89  rapidjson::Document j_doc;
90  if (!App::GetContentManager()->LoadAndParseJson(filename, RGN_SAVEGAMES, j_doc) ||
91  !j_doc.IsObject() || !j_doc.HasMember("format_version") || !j_doc["format_version"].IsNumber() ||
92  !j_doc.HasMember("terrain_name") || !j_doc["terrain_name"].IsString())
93  return "";
94 
95  return j_doc["terrain_name"].GetString();
96 }
97 
98 void GameContext::HandleSavegameHotkeys()
99 {
100  // Global savegames
101  int slot = -1;
102  if (App::GetInputEngine()->getEventBoolValueBounce(EV_COMMON_QUICKLOAD_01, 1.0f))
103  {
104  slot = 1;
105  }
106  if (App::GetInputEngine()->getEventBoolValueBounce(EV_COMMON_QUICKLOAD_02, 1.0f))
107  {
108  slot = 2;
109  }
110  if (App::GetInputEngine()->getEventBoolValueBounce(EV_COMMON_QUICKLOAD_03, 1.0f))
111  {
112  slot = 3;
113  }
114  if (App::GetInputEngine()->getEventBoolValueBounce(EV_COMMON_QUICKLOAD_04, 1.0f))
115  {
116  slot = 4;
117  }
118  if (App::GetInputEngine()->getEventBoolValueBounce(EV_COMMON_QUICKLOAD_05, 1.0f))
119  {
120  slot = 5;
121  }
122  if (App::GetInputEngine()->getEventBoolValueBounce(EV_COMMON_QUICKLOAD_06, 1.0f))
123  {
124  slot = 6;
125  }
126  if (App::GetInputEngine()->getEventBoolValueBounce(EV_COMMON_QUICKLOAD_07, 1.0f))
127  {
128  slot = 7;
129  }
130  if (App::GetInputEngine()->getEventBoolValueBounce(EV_COMMON_QUICKLOAD_08, 1.0f))
131  {
132  slot = 8;
133  }
134  if (App::GetInputEngine()->getEventBoolValueBounce(EV_COMMON_QUICKLOAD_09, 1.0f))
135  {
136  slot = 9;
137  }
138  if (App::GetInputEngine()->getEventBoolValueBounce(EV_COMMON_QUICKLOAD_10, 1.0f))
139  {
140  slot = 0;
141  }
142  if (slot != -1)
143  {
144  Ogre::String filename = Ogre::StringUtil::format("quicksave-%d.sav", slot);
146  }
147 
148  if (App::sim_terrain_name->getStr() == "" || App::sim_state->getEnum<SimState>() != SimState::RUNNING)
149  return;
150 
151  slot = -1;
152  if (App::GetInputEngine()->getEventBoolValueBounce(EV_COMMON_QUICKSAVE_01, 1.0f))
153  {
154  slot = 1;
155  }
156  if (App::GetInputEngine()->getEventBoolValueBounce(EV_COMMON_QUICKSAVE_02, 1.0f))
157  {
158  slot = 2;
159  }
160  if (App::GetInputEngine()->getEventBoolValueBounce(EV_COMMON_QUICKSAVE_03, 1.0f))
161  {
162  slot = 3;
163  }
164  if (App::GetInputEngine()->getEventBoolValueBounce(EV_COMMON_QUICKSAVE_04, 1.0f))
165  {
166  slot = 4;
167  }
168  if (App::GetInputEngine()->getEventBoolValueBounce(EV_COMMON_QUICKSAVE_05, 1.0f))
169  {
170  slot = 5;
171  }
172  if (App::GetInputEngine()->getEventBoolValueBounce(EV_COMMON_QUICKSAVE_06, 1.0f))
173  {
174  slot = 6;
175  }
176  if (App::GetInputEngine()->getEventBoolValueBounce(EV_COMMON_QUICKSAVE_07, 1.0f))
177  {
178  slot = 7;
179  }
180  if (App::GetInputEngine()->getEventBoolValueBounce(EV_COMMON_QUICKSAVE_08, 1.0f))
181  {
182  slot = 8;
183  }
184  if (App::GetInputEngine()->getEventBoolValueBounce(EV_COMMON_QUICKSAVE_09, 1.0f))
185  {
186  slot = 9;
187  }
188  if (App::GetInputEngine()->getEventBoolValueBounce(EV_COMMON_QUICKSAVE_10, 1.0f))
189  {
190  slot = 0;
191  }
192  if (slot != -1)
193  {
194  Ogre::String filename = Ogre::StringUtil::format("quicksave-%d.sav", slot);
195  App::GetGameContext()->SaveScene(filename);
196  }
197 
198  // Terrain local savegames
199 
200  if (App::GetInputEngine()->getEventBoolValueBounce(EV_COMMON_QUICKLOAD, 1.0f))
201  {
202  if (App::sim_quickload_dialog->getBool())
203  {
205  dialog->mbc_title = _LC("QuickloadDialog", "Load game?");
206  dialog->mbc_text = _LC("QuickloadDialog", "You will lose all unsaved progress!");
208 
209  GUI::MessageBoxButton ok_btn;
210  ok_btn.mbb_caption = _LC("QuickloadDialog", "Load");
213  dialog->mbc_buttons.push_back(ok_btn);
214 
215  GUI::MessageBoxButton cancel_btn;
216  cancel_btn.mbb_caption = _LC("QuickloadDialog", "Cancel");
217  dialog->mbc_buttons.push_back(cancel_btn); // No action - just close the dialog.
218 
221  }
222  else
223  {
226  App::GetGameContext()->GetQuicksaveFilename()));
227  }
228  }
229 
230  if (App::GetInputEngine()->getEventBoolValueBounce(EV_COMMON_QUICKSAVE))
231  {
232  App::GetGameContext()->SaveScene(App::GetGameContext()->GetQuicksaveFilename());
233  }
234 }
235 
236 // --------------------------------
237 // ActorManager functions
238 
239 bool ActorManager::LoadScene(Ogre::String save_filename)
240 {
241  // Read from disk
242  rapidjson::Document j_doc;
243  if (!App::GetContentManager()->LoadAndParseJson(save_filename, RGN_SAVEGAMES, j_doc) ||
244  !j_doc.IsObject() || !j_doc.HasMember("format_version") || !j_doc["format_version"].IsNumber())
245  {
247  Console::CONSOLE_MSGTYPE_INFO, Console::CONSOLE_SYSTEM_ERROR, _L("Error while loading scene: File invalid or missing"));
248  return false;
249  }
250  if (j_doc["format_version"].GetInt() != SAVEGAME_FILE_FORMAT)
251  {
253  Console::CONSOLE_MSGTYPE_INFO, Console::CONSOLE_SYSTEM_ERROR, _L("Error while loading scene: File format mismatch"));
254  return false;
255  }
256 
257  // Terrain
258  String terrain_name = j_doc["terrain_name"].GetString();
259 
260  if (App::mp_state->getEnum<MpState>() == RoR::MpState::CONNECTED)
261  {
262  if (save_filename == "autosave.sav")
263  return false;
264  if (terrain_name != App::sim_terrain_name->getStr())
265  {
267  Console::CONSOLE_MSGTYPE_INFO, Console::CONSOLE_SYSTEM_ERROR, _L("Error while loading scene: Terrain mismatch"));
268  return false;
269  }
270  if (j_doc["actors"].GetArray().Size() > 3)
271  {
273  Console::CONSOLE_MSGTYPE_INFO, Console::CONSOLE_SYSTEM_ERROR, _L("Error while loading scene: Too many vehicles"));
274  return false;
275  }
276  }
277 
278  m_forced_awake = j_doc["forced_awake"].GetBool();
279 
280  App::GetGameContext()->GetActorManager()->SetSimulationPaused(j_doc["physics_paused"].GetBool());
281 
282 #ifdef USE_CAELUM
283  if (App::gfx_sky_mode->getEnum<GfxSkyMode>() == GfxSkyMode::CAELUM)
284  {
285  if (j_doc.HasMember("daytime"))
286  {
287  App::GetGameContext()->GetTerrain()->getSkyManager()->SetTime(j_doc["daytime"].GetDouble());
288  }
289  }
290 #endif // USE_CAELUM
291 
292  // Character
293  auto data = j_doc["player_position"].GetArray();
294  Vector3 position = Vector3(data[0].GetFloat(), data[1].GetFloat(), data[2].GetFloat());
296  App::GetGameContext()->GetPlayerCharacter()->setRotation(Radian(j_doc["player_rotation"].GetFloat()));
297 
298  // Actors
299  auto actors_changed = false;
300  auto player_actor = App::GetGameContext()->GetPlayerActor();
301  auto prev_player_actor = App::GetGameContext()->GetPrevPlayerActor();
302  std::vector<ActorPtr> actors;
303  std::vector<ActorPtr> x_actors = GetLocalActors();
304  for (rapidjson::Value& j_entry: j_doc["actors"].GetArray())
305  {
306  String rigdef_filename = j_entry["filename"].GetString();
307  if (!App::GetCacheSystem()->CheckResourceLoaded(rigdef_filename))
308  {
309  Str<600> msg; msg << _L("Error while loading scene: Missing content (probably not installed)") << " '" << rigdef_filename << "'";
310  App::GetConsole()->putMessage(Console::CONSOLE_MSGTYPE_ACTOR, Console::CONSOLE_SYSTEM_ERROR, msg.ToCStr());
311  actors.push_back(nullptr);
312  continue;
313  }
314 
315  CacheEntryPtr skin = nullptr;
316  if (j_entry.HasMember("skin"))
317  {
318  skin = App::GetCacheSystem()->FetchSkinByName(j_entry["skin"].GetString());
319  }
320 
321  TuneupDefPtr working_tuneup = nullptr;
322  if (j_entry.HasMember("tuneup_document"))
323  {
324  const char* tuneup_str = j_entry["tuneup_document"].GetString();
325  size_t tuneup_len = j_entry["tuneup_document"].GetStringLength();
326  Ogre::DataStreamPtr datastream(new Ogre::MemoryDataStream((void*)tuneup_str, tuneup_len));
327  std::vector<TuneupDefPtr> tuneups = TuneupUtil::ParseTuneups(datastream);
328  ROR_ASSERT(tuneups.size() > 0);
329  working_tuneup = tuneups[0];
330  }
331 
332  String section_config = j_entry["section_config"].GetString();
333 
334  ActorPtr actor = nullptr;
335  int index = static_cast<int>(actors.size());
336  if (index < x_actors.size())
337  {
338  if (j_entry["filename"].GetString() != x_actors[index]->ar_filename ||
339  (skin != nullptr && skin->dname != x_actors[index]->m_used_skin_entry->dname) ||
340  section_config != x_actors[index]->getSectionConfig())
341  {
342  if (x_actors[index] == player_actor)
343  {
345  }
346  else if (x_actors[index] == prev_player_actor)
347  {
349  }
350  App::GetGameContext()->PushMessage(Message(MSG_SIM_DELETE_ACTOR_REQUESTED, static_cast<void*>(new ActorPtr(x_actors[index]))));
351  actors_changed = true;
352  }
353  else
354  {
355  actor = x_actors[index];
356  actor->SyncReset(false);
357  }
358  }
359 
360  if (actor == nullptr)
361  {
362  bool preloaded = j_entry["preloaded_with_terrain"].GetBool();
363 
365  rq->asr_filename = rigdef_filename;
366  rq->asr_position.x = j_entry["position"][0].GetFloat();
367  rq->asr_position.y = preloaded ? j_entry["position"][1].GetFloat() : j_entry["min_height"].GetFloat();
368  rq->asr_position.z = j_entry["position"][2].GetFloat();
369  rq->asr_rotation = Quaternion(Degree(270) - Radian(j_entry["rotation"].GetFloat()), Vector3::UNIT_Y);
370  rq->asr_skin_entry = skin;
371  rq->asr_working_tuneup = working_tuneup;
372  rq->asr_config = section_config;
373  rq->asr_origin = preloaded ? ActorSpawnRequest::Origin::TERRN_DEF : ActorSpawnRequest::Origin::SAVEGAME;
374  rq->asr_free_position = preloaded;
375  // Copy saved state
376  rq->asr_saved_state = std::shared_ptr<rapidjson::Document>(new rapidjson::Document());
377  rq->asr_saved_state->CopyFrom(j_entry, rq->asr_saved_state->GetAllocator());
378 
380  actors_changed = true;
381  // CAUTION: `actor` remains nullptr!
382  }
383 
384  actors.push_back(actor);
385  }
386  for (size_t index = actors.size(); index < x_actors.size(); index++)
387  {
388  if (x_actors[index] == player_actor)
389  {
391  }
392  else if (x_actors[index] == prev_player_actor)
393  {
395  }
396  App::GetGameContext()->PushMessage(Message(MSG_SIM_DELETE_ACTOR_REQUESTED, static_cast<void*>(new ActorPtr(x_actors[index]))));
397  actors_changed = true;
398  }
399 
400  const int num_actors = static_cast<int>(j_doc["actors"].Size());
401  for (int index = 0; index < num_actors; index++)
402  {
403  if (actors[index] == nullptr)
404  continue;
405 
406  ActorPtr actor = actors[index];
407  rapidjson::Value& j_entry = j_doc["actors"][index];
408 
409  this->RestoreSavedState(actor, j_entry);
410  }
411 
412  if (save_filename != "autosave.sav")
413  {
415  Console::CONSOLE_MSGTYPE_INFO, Console::CONSOLE_SYSTEM_NOTICE, _L("Scene loaded"));
416  }
417 
418  return true;
419 }
420 
421 bool ActorManager::SaveScene(Ogre::String filename)
422 {
423  std::vector<ActorPtr> x_actors = GetLocalActors();
424 
425  if (App::mp_state->getEnum<MpState>() == RoR::MpState::CONNECTED)
426  {
427  if (filename == "autosave.sav")
428  return false;
429  if (x_actors.size() > 3)
430  {
432  Console::CONSOLE_MSGTYPE_INFO, Console::CONSOLE_SYSTEM_ERROR, _L("Error while saving scene: Too many vehicles"));
433  return false;
434  }
435  }
436 
437  rapidjson::Document j_doc;
438  j_doc.SetObject();
439  j_doc.AddMember("format_version", SAVEGAME_FILE_FORMAT, j_doc.GetAllocator());
440 
441  // Pretty name
442  String pretty_name = App::GetCacheSystem()->GetPrettyName(App::sim_terrain_name->getStr());
443  String scene_name = StringUtil::format("%s [%d]", pretty_name.c_str(), x_actors.size());
444  j_doc.AddMember("scene_name", rapidjson::StringRef(scene_name.c_str()), j_doc.GetAllocator());
445 
446  // Terrain
447  j_doc.AddMember("terrain_name", rapidjson::StringRef(App::sim_terrain_name->getStr().c_str()), j_doc.GetAllocator());
448 
449 #ifdef USE_CAELUM
450  if (App::gfx_sky_mode->getEnum<GfxSkyMode>() == GfxSkyMode::CAELUM)
451  {
452  j_doc.AddMember("daytime", App::GetGameContext()->GetTerrain()->getSkyManager()->GetTime(), j_doc.GetAllocator());
453  }
454 #endif // USE_CAELUM
455 
456  j_doc.AddMember("forced_awake", m_forced_awake, j_doc.GetAllocator());
457 
458  j_doc.AddMember("physics_paused", App::GetGameContext()->GetActorManager()->IsSimulationPaused(), j_doc.GetAllocator());
459 
460  // Character
461  rapidjson::Value j_player_position(rapidjson::kArrayType);
462  j_player_position.PushBack(App::GetGameContext()->GetPlayerCharacter()->getPosition().x, j_doc.GetAllocator());
463  j_player_position.PushBack(App::GetGameContext()->GetPlayerCharacter()->getPosition().y, j_doc.GetAllocator());
464  j_player_position.PushBack(App::GetGameContext()->GetPlayerCharacter()->getPosition().z, j_doc.GetAllocator());
465  j_doc.AddMember("player_position", j_player_position, j_doc.GetAllocator());
466  j_doc.AddMember("player_rotation", App::GetGameContext()->GetPlayerCharacter()->getRotation().valueRadians(), j_doc.GetAllocator());
467 
468  std::map<int, int> vector_index_lookup;
469  for (ActorPtr& actor : m_actors)
470  {
471  vector_index_lookup[actor->ar_vector_index] = -1;
472  auto search = std::find_if(x_actors.begin(), x_actors.end(), [actor](ActorPtr b)
473  { return actor->ar_instance_id == b->ar_instance_id; });
474  if (search != x_actors.end())
475  {
476  vector_index_lookup[actor->ar_vector_index] = std::distance(x_actors.begin(), search);
477  }
478  }
479 
480  // Actors
481  rapidjson::Value j_actors(rapidjson::kArrayType);
482  for (ActorPtr actor : x_actors)
483  {
484  rapidjson::Value j_entry(rapidjson::kObjectType);
485 
486  j_entry.AddMember("filename", rapidjson::StringRef(actor->ar_filename.c_str()), j_doc.GetAllocator());
487  rapidjson::Value j_actor_position(rapidjson::kArrayType);
488  j_actor_position.PushBack(actor->ar_nodes[0].AbsPosition.x, j_doc.GetAllocator());
489  j_actor_position.PushBack(actor->ar_nodes[0].AbsPosition.y, j_doc.GetAllocator());
490  j_actor_position.PushBack(actor->ar_nodes[0].AbsPosition.z, j_doc.GetAllocator());
491  j_entry.AddMember("position", j_actor_position, j_doc.GetAllocator());
492  j_entry.AddMember("rotation", actor->getRotation(), j_doc.GetAllocator());
493  j_entry.AddMember("min_height", actor->getMinHeight(), j_doc.GetAllocator());
494  j_entry.AddMember("spawn_rotation", actor->m_spawn_rotation, j_doc.GetAllocator());
495  j_entry.AddMember("preloaded_with_terrain", actor->isPreloadedWithTerrain(), j_doc.GetAllocator());
496  j_entry.AddMember("sim_state", static_cast<int>(actor->ar_state), j_doc.GetAllocator());
497  j_entry.AddMember("physics_paused", actor->ar_physics_paused, j_doc.GetAllocator());
498  j_entry.AddMember("player_actor", actor==App::GetGameContext()->GetPlayerActor(), j_doc.GetAllocator());
499  j_entry.AddMember("prev_player_actor", actor==App::GetGameContext()->GetPrevPlayerActor(), j_doc.GetAllocator());
500 
501  if (actor->m_used_skin_entry)
502  {
503  j_entry.AddMember("skin", rapidjson::StringRef(actor->m_used_skin_entry->dname.c_str()), j_doc.GetAllocator());
504  }
505 
506  if (actor->getWorkingTuneupDef())
507  {
508  // Include the entire .tuneup file in the savegame.
509  rapidjson::Value j_tuneup_document(rapidjson::kStringType);
510  Str<TUNEUP_BUF_SIZE> tuneup_buf; // `Ogre::MemoryDataStream` doesn't zero-out the buffer it creates; we must supply our own zeroed memory.
511  Ogre::DataStreamPtr datastream(new Ogre::MemoryDataStream(tuneup_buf.GetBuffer(), tuneup_buf.GetCapacity()));
512  TuneupUtil::ExportTuneup(datastream, actor->getWorkingTuneupDef());
513  j_tuneup_document.SetString(datastream->getAsString().c_str(), j_doc.GetAllocator());
514  j_entry.AddMember("tuneup_document", j_tuneup_document, j_doc.GetAllocator());
515  }
516 
517  j_entry.AddMember("section_config", rapidjson::StringRef(actor->m_section_config.c_str()), j_doc.GetAllocator());
518 
519  // Engine, anti-lock brake, traction control
520  if (actor->ar_engine)
521  {
522  j_entry.AddMember("engine_gear", actor->ar_engine->GetGear(), j_doc.GetAllocator());
523  j_entry.AddMember("engine_rpm", actor->ar_engine->GetEngineRpm(), j_doc.GetAllocator());
524  j_entry.AddMember("engine_auto_mode", actor->ar_engine->GetAutoMode(), j_doc.GetAllocator());
525  j_entry.AddMember("engine_auto_select", actor->ar_engine->getAutoShift(), j_doc.GetAllocator());
526  j_entry.AddMember("engine_is_running", actor->ar_engine->isRunning(), j_doc.GetAllocator());
527  j_entry.AddMember("engine_has_contact", actor->ar_engine->hasContact(), j_doc.GetAllocator());
528  j_entry.AddMember("engine_wheel_spin", actor->ar_wheel_spin, j_doc.GetAllocator());
529  j_entry.AddMember("alb_mode", actor->alb_mode, j_doc.GetAllocator());
530  j_entry.AddMember("tc_mode", actor->tc_mode, j_doc.GetAllocator());
531  j_entry.AddMember("cc_mode", actor->cc_mode, j_doc.GetAllocator());
532  j_entry.AddMember("cc_target_rpm", actor->cc_target_rpm, j_doc.GetAllocator());
533  j_entry.AddMember("cc_target_speed", actor->cc_target_speed, j_doc.GetAllocator());
534  }
535 
536  j_entry.AddMember("hydro_dir_state", actor->ar_hydro_dir_state, j_doc.GetAllocator());
537  j_entry.AddMember("hydro_aileron_state", actor->ar_hydro_aileron_state, j_doc.GetAllocator());
538  j_entry.AddMember("hydro_rudder_state", actor->ar_hydro_rudder_state, j_doc.GetAllocator());
539  j_entry.AddMember("hydro_elevator_state", actor->ar_hydro_elevator_state, j_doc.GetAllocator());
540  j_entry.AddMember("parking_brake", actor->ar_parking_brake, j_doc.GetAllocator());
541  j_entry.AddMember("trailer_parking_brake", actor->ar_trailer_parking_brake, j_doc.GetAllocator());
542  j_entry.AddMember("avg_wheel_speed", actor->ar_avg_wheel_speed, j_doc.GetAllocator());
543  j_entry.AddMember("wheel_speed", actor->ar_wheel_speed, j_doc.GetAllocator());
544  j_entry.AddMember("wheel_spin", actor->ar_wheel_spin, j_doc.GetAllocator());
545 
546  j_entry.AddMember("custom_particles", actor->m_custom_particles_enabled, j_doc.GetAllocator());
547 
548  // Flares
549  j_entry.AddMember("lights", (int)actor->getHeadlightsVisible(), j_doc.GetAllocator());
550  j_entry.AddMember("blink_type", (int)actor->getBlinkType(), j_doc.GetAllocator());
551  // "beacon_light" was "pp_beacon_light" since release 2021.02 (savegame file format 2).
552  // It was caused by find-&-replace derp in commit 5a159ad9c0d0ffb1fa3e6f4f9c4577fab3910e3e.
553  j_entry.AddMember("beacon_light", actor->getBeaconMode(), j_doc.GetAllocator());
554  j_entry.AddMember("high_beams_on", actor->getHighBeamsVisible(), j_doc.GetAllocator());
555  j_entry.AddMember("fog_lights_on", actor->getFogLightsVisible(), j_doc.GetAllocator());
556 
557  // User-defined flares
558  rapidjson::Value j_custom_lights(rapidjson::kArrayType);
559  for (int i = 0; i < MAX_CLIGHTS; i++)
560  {
561  j_custom_lights.PushBack(actor->getCustomLightVisible(i), j_doc.GetAllocator());
562  }
563  j_entry.AddMember("custom_lights", j_custom_lights, j_doc.GetAllocator());
564 
565  // Buoyance
566  if (actor->m_buoyance)
567  {
568  j_entry.AddMember("buoyance_sink", actor->m_buoyance->sink, j_doc.GetAllocator());
569  }
570 
571  // Turboprops / Turbojets
572  rapidjson::Value j_aeroengines(rapidjson::kArrayType);
573  for (int i = 0; i < actor->ar_num_aeroengines; i++)
574  {
575  rapidjson::Value j_aeroengine(rapidjson::kObjectType);
576  j_aeroengine.AddMember("rpm", actor->ar_aeroengines[i]->getRPM(), j_doc.GetAllocator());
577  j_aeroengine.AddMember("reverse", actor->ar_aeroengines[i]->getReverse(), j_doc.GetAllocator());
578  j_aeroengine.AddMember("ignition", actor->ar_aeroengines[i]->getIgnition(), j_doc.GetAllocator());
579  j_aeroengine.AddMember("throttle", actor->ar_aeroengines[i]->getThrottle(), j_doc.GetAllocator());
580  j_aeroengines.PushBack(j_aeroengine, j_doc.GetAllocator());
581  }
582  j_entry.AddMember("aeroengines", j_aeroengines, j_doc.GetAllocator());
583 
584  // Screwprops
585  rapidjson::Value j_screwprops(rapidjson::kArrayType);
586  for (int i = 0; i < actor->ar_num_screwprops; i++)
587  {
588  rapidjson::Value j_screwprop(rapidjson::kObjectType);
589  j_screwprop.AddMember("rudder", actor->ar_screwprops[i]->getRudder(), j_doc.GetAllocator());
590  j_screwprop.AddMember("throttle", actor->ar_screwprops[i]->getThrottle(), j_doc.GetAllocator());
591  j_screwprops.PushBack(j_screwprop, j_doc.GetAllocator());
592  }
593  j_entry.AddMember("screwprops", j_screwprops, j_doc.GetAllocator());
594 
595  // Rotators
596  rapidjson::Value j_rotators(rapidjson::kArrayType);
597  for (int i = 0; i < actor->ar_num_rotators; i++)
598  {
599  j_rotators.PushBack(actor->ar_rotators[i].angle, j_doc.GetAllocator());
600  }
601  j_entry.AddMember("rotators", j_rotators, j_doc.GetAllocator());
602 
603  // Wheels
604  rapidjson::Value j_wheels(rapidjson::kArrayType);
605  for (int i = 0; i < actor->ar_num_wheels; i++)
606  {
607  j_wheels.PushBack(actor->ar_wheels[i].wh_is_detached, j_doc.GetAllocator());
608  }
609  j_entry.AddMember("wheels", j_wheels, j_doc.GetAllocator());
610 
611  // Wheel differentials
612  rapidjson::Value j_wheel_diffs(rapidjson::kArrayType);
613  for (int i = 0; i < actor->m_num_wheel_diffs; i++)
614  {
615  j_wheel_diffs.PushBack(actor->m_wheel_diffs[i]->GetActiveDiffType(), j_doc.GetAllocator());
616  }
617  j_entry.AddMember("wheel_diffs", j_wheel_diffs, j_doc.GetAllocator());
618 
619  // Axle differentials
620  rapidjson::Value j_axle_diffs(rapidjson::kArrayType);
621  for (int i = 0; i < actor->m_num_axle_diffs; i++)
622  {
623  j_axle_diffs.PushBack(actor->m_axle_diffs[i]->GetActiveDiffType(), j_doc.GetAllocator());
624  }
625  j_entry.AddMember("axle_diffs", j_axle_diffs, j_doc.GetAllocator());
626 
627  // Transfercase
628  if (actor->m_transfer_case)
629  {
630  rapidjson::Value j_transfer_case(rapidjson::kObjectType);
631  j_transfer_case.AddMember("4WD", actor->m_transfer_case->tr_4wd_mode, j_doc.GetAllocator());
632  j_transfer_case.AddMember("GearRatio", actor->m_transfer_case->tr_gear_ratios[0], j_doc.GetAllocator());
633  j_entry.AddMember("transfercase", j_transfer_case, j_doc.GetAllocator());
634  }
635 
636  // Commands
637  rapidjson::Value j_commands(rapidjson::kArrayType);
638  for (int i = 0; i < MAX_COMMANDS; i++) // BEWARE: commandkeys are indexed 1-MAX_COMMANDS! - but to preserve compatibility we omit the last commandkey in savegames.
639  {
640  rapidjson::Value j_command(rapidjson::kArrayType);
641  j_command.PushBack(actor->ar_command_key[i].commandValue, j_doc.GetAllocator());
642  j_command.PushBack(actor->ar_command_key[i].triggerInputValue, j_doc.GetAllocator());
643 
644  rapidjson::Value j_command_beams(rapidjson::kArrayType);
645  for (int j = 0; j < (int)actor->ar_command_key[i].beams.size(); j++)
646  {
647  rapidjson::Value j_cmb(rapidjson::kArrayType);
648  auto& beam = actor->ar_command_key[i].beams[j];
649  j_cmb.PushBack(beam.cmb_state->auto_moving_mode, j_doc.GetAllocator());
650  j_cmb.PushBack(beam.cmb_state->pressed_center_mode, j_doc.GetAllocator());
651  j_command_beams.PushBack(j_cmb, j_doc.GetAllocator());
652  }
653  j_command.PushBack(j_command_beams, j_doc.GetAllocator());
654 
655  j_commands.PushBack(j_command, j_doc.GetAllocator());
656  }
657  j_entry.AddMember("commands", j_commands, j_doc.GetAllocator());
658 
659  // Hooks
660  rapidjson::Value j_hooks(rapidjson::kArrayType);
661  for (const auto& h : actor->ar_hooks)
662  {
663  rapidjson::Value j_hook(rapidjson::kObjectType);
664  int lock_node = h.hk_lock_node ? h.hk_lock_node->pos : -1;
665  int locked_actor = h.hk_locked_actor ? vector_index_lookup[h.hk_locked_actor->ar_vector_index] : -1;
666  j_hook.AddMember("locked", h.hk_locked, j_doc.GetAllocator());
667  j_hook.AddMember("lock_node", lock_node, j_doc.GetAllocator());
668  j_hook.AddMember("locked_actor", locked_actor, j_doc.GetAllocator());
669  j_hooks.PushBack(j_hook, j_doc.GetAllocator());
670  }
671  j_entry.AddMember("hooks", j_hooks, j_doc.GetAllocator());
672 
673  // Ropes
674  rapidjson::Value j_ropes(rapidjson::kArrayType);
675  for (const auto& r : actor->ar_ropes)
676  {
677  rapidjson::Value j_rope(rapidjson::kObjectType);
678  int locked_ropable = r.rp_locked_ropable ? r.rp_locked_ropable->pos : -1;
679  int locked_actor = r.rp_locked_actor ? vector_index_lookup[r.rp_locked_actor->ar_vector_index] : -1;
680  j_rope.AddMember("locked", r.rp_locked, j_doc.GetAllocator());
681  j_rope.AddMember("locked_ropable", locked_ropable, j_doc.GetAllocator());
682  j_rope.AddMember("locked_actor", locked_actor, j_doc.GetAllocator());
683  j_ropes.PushBack(j_rope, j_doc.GetAllocator());
684  }
685  j_entry.AddMember("ropes", j_ropes, j_doc.GetAllocator());
686 
687  // Ties
688  rapidjson::Value j_ties(rapidjson::kArrayType);
689  for (const auto& t : actor->ar_ties)
690  {
691  rapidjson::Value j_tie(rapidjson::kObjectType);
692  int locked_ropable = t.ti_locked_ropable ? t.ti_locked_ropable->pos : -1;
693  int locked_actor = t.ti_locked_actor ? vector_index_lookup[t.ti_locked_actor->ar_vector_index] : -1;
694  j_tie.AddMember("tied", t.ti_tied, j_doc.GetAllocator());
695  j_tie.AddMember("tying", t.ti_tying, j_doc.GetAllocator());
696  j_tie.AddMember("locked_ropable", locked_ropable, j_doc.GetAllocator());
697  j_tie.AddMember("locked_actor", locked_actor, j_doc.GetAllocator());
698  j_ties.PushBack(j_tie, j_doc.GetAllocator());
699  }
700  j_entry.AddMember("ties", j_ties, j_doc.GetAllocator());
701 
702  // Ropables
703  rapidjson::Value j_ropables(rapidjson::kArrayType);
704  for (const auto& r : actor->ar_ropables)
705  {
706  rapidjson::Value j_ropable(rapidjson::kObjectType);
707  j_ropable.AddMember("attached_ties", r.attached_ties, j_doc.GetAllocator());
708  j_ropable.AddMember("attached_ropes", r.attached_ropes, j_doc.GetAllocator());
709  j_ropables.PushBack(j_ropable, j_doc.GetAllocator());
710  }
711  j_entry.AddMember("ropables", j_ropables, j_doc.GetAllocator());
712 
713  j_entry.AddMember("slidenodes_locked", actor->m_slidenodes_locked, j_doc.GetAllocator());
714 
715  // Nodes
716  rapidjson::Value j_nodes(rapidjson::kArrayType);
717  for (int i = 0; i < actor->ar_num_nodes; i++)
718  {
719  rapidjson::Value j_node(rapidjson::kArrayType);
720 
721  // Position
722  j_node.PushBack(actor->ar_nodes[i].AbsPosition.x, j_doc.GetAllocator());
723  j_node.PushBack(actor->ar_nodes[i].AbsPosition.y, j_doc.GetAllocator());
724  j_node.PushBack(actor->ar_nodes[i].AbsPosition.z, j_doc.GetAllocator());
725 
726  // Velocity
727  j_node.PushBack(actor->ar_nodes[i].Velocity.x, j_doc.GetAllocator());
728  j_node.PushBack(actor->ar_nodes[i].Velocity.y, j_doc.GetAllocator());
729  j_node.PushBack(actor->ar_nodes[i].Velocity.z, j_doc.GetAllocator());
730 
731  // Initial Position
732  j_node.PushBack(actor->ar_initial_node_positions[i].x, j_doc.GetAllocator());
733  j_node.PushBack(actor->ar_initial_node_positions[i].y, j_doc.GetAllocator());
734  j_node.PushBack(actor->ar_initial_node_positions[i].z, j_doc.GetAllocator());
735 
736  j_nodes.PushBack(j_node, j_doc.GetAllocator());
737  }
738  j_entry.AddMember("nodes", j_nodes, j_doc.GetAllocator());
739 
740  // Beams
741  rapidjson::Value j_beams(rapidjson::kArrayType);
742  for (int i = 0; i < actor->ar_num_beams; i++)
743  {
744  rapidjson::Value j_beam(rapidjson::kArrayType);
745 
746  j_beam.PushBack(actor->ar_beams[i].maxposstress, j_doc.GetAllocator());
747  j_beam.PushBack(actor->ar_beams[i].maxnegstress, j_doc.GetAllocator());
748  j_beam.PushBack(actor->ar_beams[i].minmaxposnegstress, j_doc.GetAllocator());
749  j_beam.PushBack(actor->ar_beams[i].strength, j_doc.GetAllocator());
750  j_beam.PushBack(actor->ar_beams[i].L, j_doc.GetAllocator());
751  j_beam.PushBack(actor->ar_beams[i].bm_broken, j_doc.GetAllocator());
752  j_beam.PushBack(actor->ar_beams[i].bm_disabled, j_doc.GetAllocator());
753  j_beam.PushBack(actor->ar_beams[i].bm_inter_actor, j_doc.GetAllocator());
754  ActorPtr locked_actor = actor->ar_beams[i].bm_locked_actor;
755  j_beam.PushBack(locked_actor ? vector_index_lookup[locked_actor->ar_vector_index] : -1, j_doc.GetAllocator());
756 
757  j_beams.PushBack(j_beam, j_doc.GetAllocator());
758  }
759  j_entry.AddMember("beams", j_beams, j_doc.GetAllocator());
760 
761  j_actors.PushBack(j_entry, j_doc.GetAllocator());
762  }
763  j_doc.AddMember("actors", j_actors, j_doc.GetAllocator());
764 
765  // Write to disk
766  if (!App::GetContentManager()->SerializeAndWriteJson(filename, RGN_SAVEGAMES, j_doc))
767  {
768  // Error already logged
770  Console::CONSOLE_MSGTYPE_INFO, Console::CONSOLE_SYSTEM_ERROR, _L("Error while saving scene"));
771  return false;
772  }
773 
774  if (filename != "autosave.sav")
775  {
777  Console::CONSOLE_MSGTYPE_INFO, Console::CONSOLE_SYSTEM_NOTICE, _L("Scene saved"));
778  }
779 
780  return true;
781 }
782 
783 void ActorManager::RestoreSavedState(ActorPtr actor, rapidjson::Value const& j_entry)
784 {
785  actor->m_spawn_rotation = j_entry["spawn_rotation"].GetFloat();
786  actor->ar_state = static_cast<ActorState>(j_entry["sim_state"].GetInt());
787  actor->ar_physics_paused = j_entry["physics_paused"].GetBool();
788 
789  if (j_entry["player_actor"].GetBool())
790  {
792  }
793  else if (j_entry["prev_player_actor"].GetBool())
794  {
796  }
797 
798  if (actor->ar_engine)
799  {
800  int gear = j_entry["engine_gear"].GetInt();
801  float rpm = j_entry["engine_rpm"].GetFloat();
802  int automode = j_entry["engine_auto_mode"].GetInt();
803  int autoselect = j_entry["engine_auto_select"].GetInt();
804  bool running = j_entry["engine_is_running"].GetBool();
805  bool contact = j_entry["engine_has_contact"].GetBool();
806  if (running != actor->ar_engine->isRunning())
807  {
808  if (running)
809  actor->ar_engine->StartEngine();
810  else
811  actor->ar_engine->StopEngine();
812  }
813  actor->ar_engine->PushNetworkState(rpm, 0.0f, 0.0f, gear, running, contact, automode, autoselect);
814  actor->ar_engine->SetWheelSpin(j_entry["wheel_spin"].GetFloat() * RAD_PER_SEC_TO_RPM);
815  actor->alb_mode = j_entry["alb_mode"].GetBool();
816  actor->tc_mode = j_entry["tc_mode"].GetBool();
817  actor->cc_mode = j_entry["cc_mode"].GetBool();
818  actor->cc_target_rpm = j_entry["cc_target_rpm"].GetFloat();
819  actor->cc_target_speed = j_entry["cc_target_speed"].GetFloat();
820  }
821 
822  actor->ar_hydro_dir_state = j_entry["hydro_dir_state"].GetFloat();
823  actor->ar_hydro_aileron_state = j_entry["hydro_aileron_state"].GetFloat();
824  actor->ar_hydro_rudder_state = j_entry["hydro_rudder_state"].GetFloat();
825  actor->ar_hydro_elevator_state = j_entry["hydro_elevator_state"].GetFloat();
826  actor->ar_parking_brake = j_entry["parking_brake"].GetBool();
827  actor->ar_trailer_parking_brake = j_entry["trailer_parking_brake"].GetBool();
828  actor->ar_avg_wheel_speed = j_entry["avg_wheel_speed"].GetFloat();
829  actor->ar_wheel_speed = j_entry["wheel_speed"].GetFloat();
830  actor->ar_wheel_spin = j_entry["wheel_spin"].GetFloat();
831 
832  if (actor->m_custom_particles_enabled != j_entry["custom_particles"].GetBool())
833  {
834  actor->toggleCustomParticles();
835  }
836 
837  // Flares
838  actor->setHeadlightsVisible((bool)j_entry["lights"].GetInt()); // legacy name
839  actor->setBlinkType(BlinkType(j_entry["blink_type"].GetInt()));
840  // "beacon_light" was "pp_beacon_light" since release 2021.02 (savegame file format 2).
841  // It was caused by find-&-replace derp in commit 5a159ad9c0d0ffb1fa3e6f4f9c4577fab3910e3e.
842  actor->setBeaconMode(j_entry.HasMember("beacon_light") ? j_entry["beacon_light"].GetBool() : j_entry["pp_beacon_light"].GetBool());
843  actor->setHighBeamsVisible(j_entry.HasMember("high_beams_on") ? j_entry["high_beams_on"].GetBool() : false); // (added to savegame file format 3)
844  actor->setFogLightsVisible(j_entry.HasMember("fog_lights_on") ? j_entry["fog_lights_on"].GetBool() : false); // (added to savegame file format 3)
845 
846  // User-defined flares
847  if (j_entry.HasMember("custom_lights"))
848  {
849  auto flares = j_entry["custom_lights"].GetArray();
850  for (int i = 0; i < MAX_CLIGHTS; i++)
851  {
852  actor->setCustomLightVisible(i, flares[i].GetBool());
853  }
854  }
855 
856  if (actor->m_buoyance)
857  {
858  actor->m_buoyance->sink = j_entry["buoyance_sink"].GetBool();
859  }
860 
861  auto aeroengines = j_entry["aeroengines"].GetArray();
862  for (int i = 0; i < actor->ar_num_aeroengines; i++)
863  {
864  actor->ar_aeroengines[i]->setRPM(aeroengines[i]["rpm"].GetFloat());
865  actor->ar_aeroengines[i]->setReverse(aeroengines[i]["reverse"].GetBool());
866  actor->ar_aeroengines[i]->setIgnition(aeroengines[i]["ignition"].GetBool());
867  actor->ar_aeroengines[i]->setThrottle(aeroengines[i]["throttle"].GetFloat());
868  }
869 
870  auto screwprops = j_entry["screwprops"].GetArray();
871  for (int i = 0; i < actor->ar_num_screwprops; i++)
872  {
873  actor->ar_screwprops[i]->setRudder(screwprops[i]["rudder"].GetFloat());
874  actor->ar_screwprops[i]->setThrottle(screwprops[i]["throttle"].GetFloat());
875  }
876 
877  for (int i = 0; i < actor->ar_num_rotators; i++)
878  {
879  actor->ar_rotators[i].angle = j_entry["rotators"][i].GetFloat();
880  }
881 
882  for (int i = 0; i < actor->ar_num_wheels; i++)
883  {
884  if (actor->m_skid_trails[i])
885  {
886  actor->m_skid_trails[i]->reset();
887  }
888  actor->ar_wheels[i].wh_is_detached = j_entry["wheels"][i].GetBool();
889  }
890 
891  for (int i = 0; i < actor->m_num_wheel_diffs; i++)
892  {
893  for (int k = 0; k < actor->m_wheel_diffs[i]->GetNumDiffTypes(); k++)
894  {
895  if (actor->m_wheel_diffs[i]->GetActiveDiffType() != j_entry["wheel_diffs"][i].GetInt())
897  }
898  }
899 
900  for (int i = 0; i < actor->m_num_axle_diffs; i++)
901  {
902  for (int k = 0; k < actor->m_axle_diffs[i]->GetNumDiffTypes(); k++)
903  {
904  if (actor->m_axle_diffs[i]->GetActiveDiffType() != j_entry["axle_diffs"][i].GetInt())
906  }
907  }
908 
909  if (actor->m_transfer_case)
910  {
911  actor->m_transfer_case->tr_4wd_mode = j_entry["transfercase"]["4WD"].GetBool();
912  for (int k = 0; k < actor->m_transfer_case->tr_gear_ratios.size(); k++)
913  {
914  if (actor->m_transfer_case->tr_gear_ratios[0] != j_entry["transfercase"]["GearRatio"].GetFloat())
916  }
917  }
918 
919  auto commands = j_entry["commands"].GetArray();
920  for (int i = 0; i < MAX_COMMANDS; i++) // BEWARE: commandkeys are indexed 1-MAX_COMMANDS! - but to preserve compatibility we omit the last commandkey in savegames.
921  {
922  auto& command_key = actor->ar_command_key[i];
923  command_key.commandValue = commands[i][0].GetFloat();
924  command_key.triggerInputValue = commands[i][1].GetFloat();
925  auto command_beams = commands[i][2].GetArray();
926  for (int j = 0; j < (int)command_key.beams.size(); j++)
927  {
928  command_key.beams[j].cmb_state->auto_moving_mode = command_beams[j][0].GetInt();
929  command_key.beams[j].cmb_state->pressed_center_mode = command_beams[j][1].GetBool();
930  }
931  }
932 
933  auto nodes = j_entry["nodes"].GetArray();
934  for (rapidjson::SizeType i = 0; i < nodes.Size(); i++)
935  {
936  auto data = nodes[i].GetArray();
937  actor->ar_nodes[i].AbsPosition = Vector3(data[0].GetFloat(), data[1].GetFloat(), data[2].GetFloat());
938  actor->ar_nodes[i].RelPosition = actor->ar_nodes[i].AbsPosition - actor->ar_origin;
939  actor->ar_nodes[i].Velocity = Vector3(data[3].GetFloat(), data[4].GetFloat(), data[5].GetFloat());
940  actor->ar_initial_node_positions[i] = Vector3(data[6].GetFloat(), data[7].GetFloat(), data[8].GetFloat());
941  }
942 
943  std::vector<ActorPtr> actors = this->GetLocalActors();
944 
945  auto beams = j_entry["beams"].GetArray();
946  for (rapidjson::SizeType i = 0; i < beams.Size(); i++)
947  {
948  auto data = beams[i].GetArray();
949  actor->ar_beams[i].maxposstress = data[0].GetFloat();
950  actor->ar_beams[i].maxnegstress = data[1].GetFloat();
951  actor->ar_beams[i].minmaxposnegstress = data[2].GetFloat();
952  actor->ar_beams[i].strength = data[3].GetFloat();
953  actor->ar_beams[i].L = data[4].GetFloat();
954  actor->ar_beams[i].bm_broken = data[5].GetBool();
955  actor->ar_beams[i].bm_disabled = data[6].GetBool();
956  actor->ar_beams[i].bm_inter_actor = data[7].GetBool();
957  int locked_actor = data[8].GetInt();
958  if (locked_actor != -1 &&
959  locked_actor < (int)actors.size() &&
960  actors[locked_actor] != nullptr)
961  {
962  actor->AddInterActorBeam(&actor->ar_beams[i], actors[locked_actor], ActorLinkingRequestType::LOAD_SAVEGAME); // OK to be invoked here - RestoreSavedState() - processing MSG_SIM_MODIFY_ACTOR_REQUESTED
963  }
964  }
965 
966  auto hooks = j_entry["hooks"].GetArray();
967  for (int i = 0; i < actor->ar_hooks.size(); i++)
968  {
969  int lock_node = hooks[i]["lock_node"].GetInt();
970  int locked_actor = hooks[i]["locked_actor"].GetInt();
971  if (lock_node != -1 &&
972  locked_actor != -1 &&
973  locked_actor < (int)actors.size() &&
974  actors[locked_actor] != nullptr)
975  {
976  actor->ar_hooks[i].hk_locked = HookState(hooks[i]["locked"].GetInt());
977  actor->ar_hooks[i].hk_locked_actor = actors[locked_actor];
978  actor->ar_hooks[i].hk_lock_node = &actors[locked_actor]->ar_nodes[lock_node];
979  if (actor->ar_hooks[i].hk_beam->bm_inter_actor)
980  {
981  actor->ar_hooks[i].hk_beam->p2 = actor->ar_hooks[i].hk_lock_node;
982  }
983  }
984  }
985 
986  auto ropes = j_entry["ropes"].GetArray();
987  for (int i = 0; i < actor->ar_ropes.size(); i++)
988  {
989  int ropable = ropes[i]["locked_ropable"].GetInt();
990  int locked_actor = ropes[i]["locked_actor"].GetInt();
991  if (ropable != -1 &&
992  locked_actor != -1 &&
993  locked_actor < (int)actors.size() &&
994  actors[locked_actor] != nullptr)
995  {
996  actor->ar_ropes[i].rp_locked = ropes[i]["locked"].GetInt();
997  actor->ar_ropes[i].rp_locked_actor = actors[locked_actor];
998  actor->ar_ropes[i].rp_locked_ropable = &actors[locked_actor]->ar_ropables[ropable];
999  }
1000  }
1001 
1002  auto ties = j_entry["ties"].GetArray();
1003  for (int i = 0; i < actor->ar_ties.size(); i++)
1004  {
1005  int ropable = ties[i]["locked_ropable"].GetInt();
1006  int locked_actor = ties[i]["locked_actor"].GetInt();
1007  if (ropable != -1 &&
1008  locked_actor != -1 &&
1009  locked_actor < (int)actors.size() &&
1010  actors[locked_actor] != nullptr)
1011  {
1012  actor->ar_ties[i].ti_tied = ties[i]["tied"].GetBool();
1013  actor->ar_ties[i].ti_tying = ties[i]["tying"].GetBool();
1014  actor->ar_ties[i].ti_locked_actor = actors[locked_actor];
1015  actor->ar_ties[i].ti_locked_ropable = &actors[locked_actor]->ar_ropables[ropable];
1016  if (actor->ar_ties[i].ti_beam->bm_inter_actor)
1017  {
1018  actor->ar_ties[i].ti_beam->p2 = actor->ar_ties[i].ti_locked_ropable->node;
1019  }
1020  }
1021  }
1022 
1023  auto ropables = j_entry["ropables"].GetArray();
1024  for (int i = 0; i < actor->ar_ropables.size(); i++)
1025  {
1026  actor->ar_ropables[i].attached_ties = ropables[i]["attached_ties"].GetInt();
1027  actor->ar_ropables[i].attached_ropes = ropables[i]["attached_ropes"].GetInt();
1028  }
1029 
1030  actor->resetSlideNodes();
1031  if (actor->m_slidenodes_locked != j_entry["slidenodes_locked"].GetBool())
1032  {
1033  actor->toggleSlideNodeLock(); // OK to be invoked here - RestoreSavedState() - processing MSG_SIM_MODIFY_ACTOR_REQUESTED
1034  }
1035 
1036  actor->UpdateBoundingBoxes();
1037  actor->calculateAveragePosition();
1039 }
RoR::GUI::MessageBoxConfig::mbc_buttons
std::vector< MessageBoxButton > mbc_buttons
Definition: GUI_MessageBox.h:59
RoR::Actor::setHighBeamsVisible
void setHighBeamsVisible(bool val)
Definition: Actor.h:190
ROR_ASSERT
#define ROR_ASSERT(_EXPR)
Definition: Application.h:40
GameContext.h
Game state manager and message-queue provider.
RoR::Actor::ar_avg_wheel_speed
float ar_avg_wheel_speed
Physics state; avg wheel speed in m/s.
Definition: Actor.h:402
MAX_COMMANDS
static const int MAX_COMMANDS
maximum number of commands per actor
Definition: SimConstants.h:28
SAVEGAME_FILE_FORMAT
#define SAVEGAME_FILE_FORMAT
Definition: Savegame.cpp:47
RoR::App::sim_quickload_dialog
CVar * sim_quickload_dialog
Definition: Application.cpp:110
RoR::Actor::cc_mode
bool cc_mode
Cruise Control.
Definition: Actor.h:364
RoR::Character::setPosition
void setPosition(Ogre::Vector3 position)
Definition: Character.cpp:85
RoR::App::GetContentManager
ContentManager * GetContentManager()
Definition: Application.cpp:267
RoR::MSG_GUI_SHOW_MESSAGE_BOX_REQUESTED
@ MSG_GUI_SHOW_MESSAGE_BOX_REQUESTED
Payload = MessageBoxConfig* (owner)
Definition: Application.h:138
RoR::CacheEntry::dname
Ogre::String dname
name parsed from the file
Definition: CacheSystem.h:70
RoR::ActorSpawnRequest::asr_free_position
bool asr_free_position
Disables the automatic spawn position adjustment.
Definition: SimData.h:863
RoR::EngineSim::PushNetworkState
void PushNetworkState(float engine_rpm, float acc, float clutch, int gear, bool running, bool contact, char auto_mode, char auto_select=-1)
Sets current engine state;.
Definition: EngineSim.cpp:885
RoR::node_t::Velocity
Ogre::Vector3 Velocity
Definition: SimData.h:295
y
float y
Definition: (ValueTypes) quaternion.h:6
RoR::EngineSim::isRunning
bool isRunning() const
Definition: EngineSim.h:93
RoR::EV_COMMON_QUICKLOAD_10
@ EV_COMMON_QUICKLOAD_10
Definition: InputEngine.h:392
RoR::Actor::ar_hydro_dir_state
float ar_hydro_dir_state
Definition: Actor.h:404
RoR::Actor::ar_physics_paused
bool ar_physics_paused
Sim state.
Definition: Actor.h:484
RoR::MpState::CONNECTED
@ CONNECTED
RoR::Str::GetBuffer
char * GetBuffer()
Definition: Str.h:48
MAX_CLIGHTS
static const int MAX_CLIGHTS
See RoRnet::Lightmask and enum events in InputEngine.h.
Definition: SimConstants.h:35
RoR::Actor::setHeadlightsVisible
void setHeadlightsVisible(bool val)
Definition: Actor.h:188
RoR::Actor::m_num_wheel_diffs
int m_num_wheel_diffs
Physics attr.
Definition: Actor.h:572
RoR::ActorSpawnRequest::asr_origin
Origin asr_origin
Definition: SimData.h:857
RoR::Actor::ar_vector_index
unsigned int ar_vector_index
Sim attr; actor element index in std::vector<m_actors>
Definition: Actor.h:377
RoR::node_t::AbsPosition
Ogre::Vector3 AbsPosition
absolute position in the world (shaky)
Definition: SimData.h:294
GUI_MessageBox.h
Generic UI dialog (not modal). Invocable from scripting. Any number of buttons. Configurable to fire ...
RoR::Actor::ar_parking_brake
bool ar_parking_brake
Definition: Actor.h:414
RoR::Differential::GetActiveDiffType
DiffType GetActiveDiffType() const
Definition: Differentials.h:79
z
float z
Definition: (ValueTypes) quaternion.h:7
RoR::Actor::cc_target_rpm
float cc_target_rpm
Cruise Control.
Definition: Actor.h:366
SkyManager.h
ContentManager.h
RoR::Actor::m_num_axle_diffs
int m_num_axle_diffs
Physics attr.
Definition: Actor.h:570
RoR::Actor::m_wheel_diffs
Differential * m_wheel_diffs[MAX_WHEELS/2]
Physics.
Definition: Actor.h:571
format
Truck file format(technical spec)
RoR::Terrain::getSkyManager
SkyManager * getSkyManager()
Definition: Terrain.cpp:513
RoR::GameContext::GetPlayerCharacter
Character * GetPlayerCharacter()
Definition: GameContext.cpp:873
RoR::Str::GetCapacity
size_t GetCapacity() const
Definition: Str.h:49
RoR::Actor::ar_engine
EngineSim * ar_engine
Definition: Actor.h:379
RoR::EV_COMMON_QUICKLOAD_01
@ EV_COMMON_QUICKLOAD_01
Definition: InputEngine.h:383
RoR::MpState
MpState
Definition: Application.h:169
RoR::beam_t::strength
float strength
Definition: SimData.h:343
RoR::Actor::toggleCustomParticles
void toggleCustomParticles()
Definition: Actor.cpp:3174
RoR::Actor::ar_num_rotators
int ar_num_rotators
Definition: Actor.h:294
RoR::EV_COMMON_QUICKSAVE_07
@ EV_COMMON_QUICKSAVE_07
Definition: InputEngine.h:378
Console.h
RoR::beam_t::bm_locked_actor
ActorPtr bm_locked_actor
in case p2 is on another actor
Definition: SimData.h:350
RoR::Console::putMessage
void putMessage(MessageArea area, MessageType type, std::string const &msg, std::string icon="")
Definition: Console.cpp:97
RoR::Actor::ar_hooks
std::vector< hook_t > ar_hooks
Definition: Actor.h:302
RoR::Actor::ar_trailer_parking_brake
bool ar_trailer_parking_brake
Definition: Actor.h:415
RoR::TransferCase::tr_4wd_mode
bool tr_4wd_mode
Enables 4WD mode.
Definition: Differentials.h:53
RoR::Actor::ar_ties
std::vector< tie_t > ar_ties
Definition: Actor.h:301
RoR::GUI::MessageBoxButton::mbb_caption
std::string mbb_caption
Definition: GUI_MessageBox.h:43
RoR::ActorSpawnRequest::asr_working_tuneup
TuneupDefPtr asr_working_tuneup
Only filled when editing tuneup via Tuning menu.
Definition: SimData.h:856
TuneupFileFormat.h
The vehicle tuning system; applies addonparts and user overrides to vehicles.
RoR::Actor::m_avg_node_position_prev
Ogre::Vector3 m_avg_node_position_prev
Definition: Actor.h:553
RoR::AeroEngine::setReverse
virtual void setReverse(bool val)=0
RoR::EngineSim::SetWheelSpin
void SetWheelSpin(float rpm)
Set current wheel spinning speed.
Definition: EngineSim.cpp:933
RoR::TransferCase::tr_gear_ratios
std::vector< float > tr_gear_ratios
Gear reduction ratios.
Definition: Differentials.h:54
RoR::Screwprop::setRudder
void setRudder(float val)
Definition: ScrewProp.cpp:89
RoR::App::sim_state
CVar * sim_state
Definition: Application.cpp:96
RoR::EV_COMMON_QUICKSAVE_06
@ EV_COMMON_QUICKSAVE_06
Definition: InputEngine.h:377
RoR::Actor::ar_hydro_rudder_state
float ar_hydro_rudder_state
Definition: Actor.h:409
RoR::ActorSpawnRequest::asr_filename
std::string asr_filename
Definition: SimData.h:849
RoR::node_t::RelPosition
Ogre::Vector3 RelPosition
relative to the local physics origin (one origin per actor) (shaky)
Definition: SimData.h:293
Language.h
RoR::EV_COMMON_QUICKLOAD_09
@ EV_COMMON_QUICKLOAD_09
Definition: InputEngine.h:391
RoR::Actor::m_skid_trails
Skidmark * m_skid_trails[MAX_WHEELS *2]
Definition: Actor.h:591
RefCountingObjectPtr< CacheEntry >
GUIManager.h
Actor.h
RoR::Actor::setBlinkType
void setBlinkType(BlinkType blink)
Definition: Actor.cpp:3088
RoR::ActorSpawnRequest
Definition: SimData.h:832
EngineSim.h
RoR::Actor::ar_wheel_speed
float ar_wheel_speed
Physics state; wheel speed in m/s.
Definition: Actor.h:400
RoR::App::mp_state
CVar * mp_state
Definition: Application.cpp:115
RoR::EV_COMMON_QUICKSAVE
@ EV_COMMON_QUICKSAVE
quicksave scene to the disk
Definition: InputEngine.h:248
RoR::EV_COMMON_QUICKSAVE_09
@ EV_COMMON_QUICKSAVE_09
Definition: InputEngine.h:380
RoR::ActorSpawnRequest::asr_config
Ogre::String asr_config
Definition: SimData.h:850
RoR::Actor::ar_aeroengines
AeroEngine * ar_aeroengines[MAX_AEROENGINES]
Definition: Actor.h:329
ScrewProp.h
RoR::Actor::ar_screwprops
Screwprop * ar_screwprops[MAX_SCREWPROPS]
Definition: Actor.h:331
RoR::Actor::ar_beams
beam_t * ar_beams
Definition: Actor.h:287
RoR::Actor::ar_num_aeroengines
int ar_num_aeroengines
Definition: Actor.h:330
RoR::CVar::getStr
std::string const & getStr() const
Definition: CVar.h:95
RoR::Actor::ar_rotators
rotator_t * ar_rotators
Definition: Actor.h:293
RoR::Str
Wrapper for classic c-string (local buffer) Refresher: strlen() excludes '\0' terminator; strncat() A...
Definition: Str.h:35
RoR::Actor::m_transfer_case
TransferCase * m_transfer_case
Physics.
Definition: Actor.h:573
RoR::EV_COMMON_QUICKLOAD_06
@ EV_COMMON_QUICKLOAD_06
Definition: InputEngine.h:388
RAD_PER_SEC_TO_RPM
static const float RAD_PER_SEC_TO_RPM
Convert radian/second to RPM (60/2*PI)
Definition: SimConstants.h:37
RoR::Actor::m_slidenodes_locked
bool m_slidenodes_locked
Physics state; Are SlideNodes locked?
Definition: Actor.h:623
RoR::MSG_SIM_SEAT_PLAYER_REQUESTED
@ MSG_SIM_SEAT_PLAYER_REQUESTED
Payload = RoR::ActorPtr (owner) | nullptr.
Definition: Application.h:122
RoR::GUI::MessageBoxButton
Definition: GUI_MessageBox.h:41
RoR::Actor::AddInterActorBeam
void AddInterActorBeam(beam_t *beam, ActorPtr other, ActorLinkingRequestType type)
Do not call directly - use MSG_SIM_ACTOR_LINKING_REQUESTED
Definition: Actor.cpp:3317
CacheSystem.h
A database of user-installed content alias 'mods' (vehicles, terrains...)
RoR::Actor::cc_target_speed
float cc_target_speed
Cruise Control.
Definition: Actor.h:367
RoR::EV_COMMON_QUICKLOAD_02
@ EV_COMMON_QUICKLOAD_02
Definition: InputEngine.h:384
RoR::EV_COMMON_QUICKLOAD_07
@ EV_COMMON_QUICKLOAD_07
Definition: InputEngine.h:389
RoR::GameContext::PushMessage
void PushMessage(Message m)
Doesn't guarantee order! Use ChainMessage() if order matters.
Definition: GameContext.cpp:65
RoR::EV_COMMON_QUICKLOAD_05
@ EV_COMMON_QUICKLOAD_05
Definition: InputEngine.h:387
RoR::GUI::MessageBoxConfig::mbc_title
std::string mbc_title
Definition: GUI_MessageBox.h:52
RoR::Actor::ar_origin
Ogre::Vector3 ar_origin
Physics state; base position for softbody nodes.
Definition: Actor.h:385
RoR::Str::ToCStr
const char * ToCStr() const
Definition: Str.h:46
RoR::App::sim_terrain_name
CVar * sim_terrain_name
Definition: Application.cpp:97
RoR::EV_COMMON_QUICKSAVE_02
@ EV_COMMON_QUICKSAVE_02
Definition: InputEngine.h:373
RoR::Actor::setFogLightsVisible
void setFogLightsVisible(bool val)
Definition: Actor.h:192
RoR::Actor::SyncReset
void SyncReset(bool reset_position)
this one should be called only synchronously (without physics running in background)
Definition: Actor.cpp:1600
RoR::Actor::ar_command_key
CmdKeyArray ar_command_key
BEWARE: commandkeys are indexed 1-MAX_COMMANDS!
Definition: Actor.h:305
RoR::AeroEngine::setRPM
virtual void setRPM(float _rpm)=0
RoR::CacheSystem::GetPrettyName
Ogre::String GetPrettyName(Ogre::String fname)
Definition: CacheSystem.cpp:515
RoR::EV_COMMON_QUICKLOAD
@ EV_COMMON_QUICKLOAD
quickload scene from the disk
Definition: InputEngine.h:247
PlatformUtils.h
Platform-specific utilities. We use narrow UTF-8 encoded strings as paths. Inspired by http://utf8eve...
RoR::GameContext::SetPrevPlayerActor
void SetPrevPlayerActor(ActorPtr actor)
Definition: GameContext.cpp:815
RoR::HookState
HookState
Definition: SimData.h:81
RoR::Actor::ar_hydro_aileron_state
float ar_hydro_aileron_state
Definition: Actor.h:407
RoR::Screwprop::setThrottle
void setThrottle(float val)
Definition: ScrewProp.cpp:76
RoR::Differential::GetNumDiffTypes
int GetNumDiffTypes()
Definition: Differentials.h:80
Application.h
Central state/object manager and communications hub.
RoR::App::GetConsole
Console * GetConsole()
Definition: Application.cpp:270
RoR::EV_COMMON_QUICKSAVE_08
@ EV_COMMON_QUICKSAVE_08
Definition: InputEngine.h:379
RoR::GameContext::GetPrevPlayerActor
const ActorPtr & GetPrevPlayerActor()
Definition: GameContext.h:135
RoR::App::GetGameContext
GameContext * GetGameContext()
Definition: Application.cpp:280
RoR::CVar::getEnum
T getEnum() const
Definition: CVar.h:99
RoR::GUI::MessageBoxConfig::mbc_text
std::string mbc_text
Definition: GUI_MessageBox.h:53
RoR::Actor::m_spawn_rotation
float m_spawn_rotation
Definition: Actor.h:561
RoR::Actor::ar_num_screwprops
int ar_num_screwprops
Definition: Actor.h:332
RoR::BlinkType
BlinkType
< Turn signal
Definition: SimData.h:121
RoR::GameContext::GetQuicksaveFilename
std::string GetQuicksaveFilename()
For currently loaded terrain (cvar 'sim_terrain_name')
Definition: Savegame.cpp:55
RoR::ActorSpawnRequest::asr_skin_entry
CacheEntryPtr asr_skin_entry
Definition: SimData.h:854
RoR::Actor::ar_wheel_spin
float ar_wheel_spin
Physics state; wheel speed in radians/s.
Definition: Actor.h:401
RoR::Differential::ToggleDifferentialMode
void ToggleDifferentialMode()
Definition: Differentials.cpp:27
RoR::App::gfx_sky_mode
CVar * gfx_sky_mode
Definition: Application.cpp:219
RoR::ActorState
ActorState
Definition: SimData.h:265
RoR::Actor::toggleSlideNodeLock
void toggleSlideNodeLock()
Definition: ActorSlideNode.cpp:34
_LC
#define _LC(ctx, str)
Definition: Language.h:42
RoR::Actor::tc_mode
bool tc_mode
Traction control state; Enabled? {1/0}.
Definition: Actor.h:357
RoR::Actor::ar_hydro_elevator_state
float ar_hydro_elevator_state
Definition: Actor.h:411
RoR::EV_COMMON_QUICKSAVE_04
@ EV_COMMON_QUICKSAVE_04
Definition: InputEngine.h:375
RoR::GUI::MessageBoxButton::mbb_mq_message
MsgType mbb_mq_message
Message to queue on click.
Definition: GUI_MessageBox.h:44
RoR::AeroEngine::setIgnition
virtual void setIgnition(bool val)=0
Skidmark.h
RoR::GUI::MessageBoxConfig::mbc_always_ask_conf
CVar * mbc_always_ask_conf
If set, displays classic checkbox "[x] Always ask".
Definition: GUI_MessageBox.h:54
RoR::Actor::alb_mode
bool alb_mode
Anti-lock brake state; Enabled? {1/0}.
Definition: Actor.h:350
RoR::Actor::setBeaconMode
void setBeaconMode(bool val)
Definition: Actor.h:193
RoR::beam_t::bm_inter_actor
bool bm_inter_actor
in case p2 is on another actor
Definition: SimData.h:349
RoR::Actor::ar_initial_node_positions
std::vector< Ogre::Vector3 > ar_initial_node_positions
Definition: Actor.h:311
RoR::App::GetCacheSystem
CacheSystem * GetCacheSystem()
Definition: Application.cpp:272
RoR::EngineSim::StopEngine
void StopEngine()
stall engine
Definition: EngineSim.cpp:1062
RoR::CacheSystem::FetchSkinByName
CacheEntryPtr FetchSkinByName(std::string const &skin_name)
Definition: CacheSystem.cpp:1559
RoR::Actor::ar_nodes
node_t * ar_nodes
Definition: Actor.h:279
RoR::wheel_t::wh_is_detached
bool wh_is_detached
Definition: SimData.h:454
RoR::GUI::MessageBoxConfig
Definition: GUI_MessageBox.h:50
Buoyance.h
RoR::Message
Unified game event system - all requests and state changes are reported using a message.
Definition: GameContext.h:51
_L
#define _L
Definition: ErrorUtils.cpp:34
RoR::Actor::m_axle_diffs
Differential * m_axle_diffs[1+MAX_WHEELS/2]
Physics.
Definition: Actor.h:569
RoR::Actor::ar_ropes
std::vector< rope_t > ar_ropes
Definition: Actor.h:299
RoR::Actor::resetSlideNodes
void resetSlideNodes()
Reset all the SlideNodes.
Definition: ActorSlideNode.cpp:122
RoR::EV_COMMON_QUICKSAVE_10
@ EV_COMMON_QUICKSAVE_10
Definition: InputEngine.h:381
RoR::EngineSim::StartEngine
void StartEngine()
Quick engine start. Plays sounds.
Definition: EngineSim.cpp:998
RoR::beam_t::maxnegstress
float maxnegstress
Definition: SimData.h:342
nodes
or anywhere else will not be considered a but parsed as regular data ! Each line is treated as values separated by separators Possible i e animators Multiline description Single does not affect it Directive usualy set global attributes or change behavior of the parsing Directive may appear in any block section Modularity The elements can be grouped into modules Each module must belong to one or more configurations Directives sectionconfig specify truck configurations the user can choose from Exactly one must be selected If the first defined is used lettercase matches original docs(parsing is insensitive). NAME TYPE NOTES advdrag BLOCK add_animation DIRECTIVE Special syntax airbrakes BLOCK animators BLOCK Special syntax IF(values[0]=="") bad trailing chars are silently ignored no space at the end Items delimited On each side of there is max item Empty invalid string parses as node num items Acceptable item the node is the others When a node range has more than nodes
Definition: ReadMe.txt:302
RoR::beam_t::minmaxposnegstress
float minmaxposnegstress
Definition: SimData.h:340
RoR::Actor::toggleTransferCaseGearRatio
void toggleTransferCaseGearRatio()
Definition: Actor.cpp:1465
RoR::MSG_SIM_SPAWN_ACTOR_REQUESTED
@ MSG_SIM_SPAWN_ACTOR_REQUESTED
Payload = RoR::ActorSpawnRequest* (owner)
Definition: Application.h:119
RoR::Actor::ar_num_wheels
int ar_num_wheels
Definition: Actor.h:324
RoR::App::GetInputEngine
InputEngine * GetInputEngine()
Definition: Application.cpp:271
RoR::Actor::m_avg_node_position
Ogre::Vector3 m_avg_node_position
average node position
Definition: Actor.h:551
RoR::ActorPtr
RefCountingObjectPtr< Actor > ActorPtr
Definition: ForwardDeclarations.h:194
RoR::MSG_SIM_DELETE_ACTOR_REQUESTED
@ MSG_SIM_DELETE_ACTOR_REQUESTED
Payload = RoR::ActorPtr* (owner)
Definition: Application.h:121
RoR::Actor::setCustomLightVisible
void setCustomLightVisible(int number, bool visible)
Definition: Actor.cpp:4495
RoR::ActorManager::SetSimulationPaused
void SetSimulationPaused(bool v)
Definition: ActorManager.h:95
RoR::AeroEngine::setThrottle
virtual void setThrottle(float val)=0
RoR::rotator_t::angle
float angle
Definition: SimData.h:606
Terrain.h
AeroEngine.h
InputEngine.h
Handles controller inputs from player. Defines input events and binding mechanism,...
RGN_SAVEGAMES
#define RGN_SAVEGAMES
Definition: Application.h:50
RoR::GameContext::SaveScene
void SaveScene(std::string const &filename)
Definition: Savegame.cpp:69
Ogre
Definition: ExtinguishableFireAffector.cpp:35
RoR::Actor::calculateAveragePosition
void calculateAveragePosition()
Definition: Actor.cpp:1133
RoR::EV_COMMON_QUICKLOAD_04
@ EV_COMMON_QUICKLOAD_04
Definition: InputEngine.h:386
RoR::ActorSpawnRequest::asr_position
Ogre::Vector3 asr_position
Definition: SimData.h:851
RoR::Actor::ar_wheels
wheel_t ar_wheels[MAX_WHEELS]
Definition: Actor.h:323
RoR::Actor::m_custom_particles_enabled
bool m_custom_particles_enabled
Gfx state.
Definition: Actor.h:628
RoR::Actor::ar_ropables
std::vector< ropable_t > ar_ropables
Definition: Actor.h:300
RoR::EV_COMMON_QUICKSAVE_03
@ EV_COMMON_QUICKSAVE_03
Definition: InputEngine.h:374
RoR::Actor::ar_state
ActorState ar_state
Definition: Actor.h:446
RoR::GameContext::GetPlayerActor
const ActorPtr & GetPlayerActor()
Definition: GameContext.h:134
RoR::MSG_SIM_LOAD_SAVEGAME_REQUESTED
@ MSG_SIM_LOAD_SAVEGAME_REQUESTED
Definition: Application.h:117
RoR::ActorSpawnRequest::asr_rotation
Ogre::Quaternion asr_rotation
Definition: SimData.h:852
RoR::Actor::UpdateBoundingBoxes
void UpdateBoundingBoxes()
Definition: Actor.cpp:1168
RoR
Definition: AppContext.h:36
RoR::EV_COMMON_QUICKSAVE_05
@ EV_COMMON_QUICKSAVE_05
Definition: InputEngine.h:376
x
float x
Definition: (ValueTypes) quaternion.h:5
RoR::GameContext::GetActorManager
ActorManager * GetActorManager()
Definition: GameContext.h:127
RoR::GUI::MessageBoxButton::mbb_mq_description
std::string mbb_mq_description
Message argument to queue on click.
Definition: GUI_MessageBox.h:45
RoR::EV_COMMON_QUICKLOAD_08
@ EV_COMMON_QUICKLOAD_08
Definition: InputEngine.h:390
RoR::beam_t::bm_disabled
bool bm_disabled
Definition: SimData.h:351
RoR::Skidmark::reset
void reset()
Definition: Skidmark.cpp:312
RoR::Character::setRotation
void setRotation(Ogre::Radian rotation)
Definition: Character.cpp:98
RoR::Actor::m_buoyance
std::unique_ptr< Buoyance > m_buoyance
Physics.
Definition: Actor.h:587
RoR::beam_t::L
float L
length
Definition: SimData.h:339
RoR::beam_t::bm_broken
bool bm_broken
Definition: SimData.h:352
RoR::EV_COMMON_QUICKLOAD_03
@ EV_COMMON_QUICKLOAD_03
Definition: InputEngine.h:385
RoR::ActorSpawnRequest::asr_saved_state
std::shared_ptr< rapidjson::Document > asr_saved_state
Pushes msg MODIFY_ACTOR (type RESTORE_SAVED) after spawn.
Definition: SimData.h:867
RoR::GameContext::GetTerrain
const TerrainPtr & GetTerrain()
Definition: GameContext.h:117
RoR::beam_t::maxposstress
float maxposstress
Definition: SimData.h:341
RoR::EV_COMMON_QUICKSAVE_01
@ EV_COMMON_QUICKSAVE_01
Definition: InputEngine.h:372