Skip to content

Commit

Permalink
🎮 Added node & wheel tweaks to .addonpart system.
Browse files Browse the repository at this point in the history
There are 2 new directives in the addonpart format:
* `addonpart_tweak_node <nodenum> <posX> <posY> <posZ>`
* `addonpart_tweak_wheel <wheel ID> <rim mesh> <tire radius> <rim radius>`
  • Loading branch information
ohlidalp committed Nov 6, 2023
1 parent a7bdb68 commit d7f313a
Show file tree
Hide file tree
Showing 8 changed files with 352 additions and 47 deletions.
27 changes: 27 additions & 0 deletions source/main/gui/panels/GUI_TopMenubar.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1563,6 +1563,8 @@ void TopMenubar::Draw(float dt)
{
for (CacheQueryResult& addonpart_result: tuning_addonparts.cqy_results)
{
ImGui::PushID(addonpart_result.cqr_entry->fname.c_str());

bool used = tuning_actor->getUsedTuneupEntry()->tuneup_def->use_addonparts.count(addonpart_result.cqr_entry->fname) > 0;
if (ImGui::Checkbox(addonpart_result.cqr_entry->dname.c_str(), &used))
{
Expand All @@ -1574,6 +1576,31 @@ void TopMenubar::Draw(float dt)
req->mpr_target_actor = tuning_actor;
App::GetGameContext()->PushMessage(Message(MSG_EDI_MODIFY_PROJECT_REQUESTED, req));
}
// Reload button
ImGui::SameLine();
ImGui::Dummy(ImVec2(10.f, 1.f));
ImGui::SameLine();
if (ImGui::SmallButton(_LC("Tuning", "Reload")))
{
// Create spawn request while actor still exists
// Note we don't use `ActorModifyRequest::Type::RELOAD` because we don't need the bundle reloaded.
ActorSpawnRequest* srq = new ActorSpawnRequest;
srq->asr_position = Ogre::Vector3(tuning_actor->getPosition().x, tuning_actor->getMinHeight(), tuning_actor->getPosition().z);
srq->asr_rotation = Ogre::Quaternion(Ogre::Degree(270) - Ogre::Radian(tuning_actor->getRotation()), Ogre::Vector3::UNIT_Y);
srq->asr_config = tuning_actor->getSectionConfig();
srq->asr_skin_entry = tuning_actor->getUsedSkinEntry();
srq->asr_tuneup_entry = tuneup_entry;
srq->asr_cache_entry = tuning_actor->getUsedActorEntry();
srq->asr_debugview = (int)tuning_actor->GetGfxActor()->GetDebugView();
srq->asr_origin = ActorSpawnRequest::Origin::USER;

// Request bundle reloading and chain the actor delete/spawn messages to it.
App::GetGameContext()->PushMessage(Message(MSG_EDI_RELOAD_BUNDLE_REQUESTED, new CacheEntryPtr(addonpart_result.cqr_entry)));
App::GetGameContext()->ChainMessage(Message(MSG_SIM_DELETE_ACTOR_REQUESTED, new ActorPtr(tuning_actor)));
App::GetGameContext()->ChainMessage(Message(MSG_SIM_SPAWN_ACTOR_REQUESTED, srq));
}

ImGui::PopID(); //(addonpart_result.cqr_entry->fname.c_str());
}

if (ImGui::Button(_LC("Tuning", "Browse all parts")))
Expand Down
60 changes: 40 additions & 20 deletions source/main/physics/ActorSpawner.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -90,7 +90,7 @@ using namespace RoR;
/* -------------------------------------------------------------------------- */

void ActorSpawner::ConfigureSections(Ogre::String const & sectionconfig, RigDef::DocumentPtr def)
{
{
m_selected_modules.push_back(def->root_module);
if (sectionconfig != "")
{
Expand Down Expand Up @@ -122,6 +122,7 @@ void ActorSpawner::ConfigureAddonParts(CacheEntryPtr& tuneup_entry)
if (addonpart_entry)
{
AddonPartUtility util;
util.ResolveUnwantedAndTweakedElements(tuneup_entry->tuneup_def, addonpart_entry);
auto module = util.TransformToRigDefModule(addonpart_entry);
if (module)
{
Expand Down Expand Up @@ -4082,6 +4083,7 @@ void ActorSpawner::ProcessShock(RigDef::Shock & def)
void ActorSpawner::ProcessFlexBodyWheel(RigDef::FlexBodyWheel & def)
{
unsigned int base_node_index = m_actor->ar_num_nodes;
const int wheel_id = (int)m_actor->ar_num_wheels;
wheel_t & wheel = m_actor->ar_wheels[m_actor->ar_num_wheels];

node_t *axis_node_1 = &m_actor->ar_nodes[this->GetNodeIndexOrThrow(def.nodes[0])];
Expand All @@ -4105,11 +4107,16 @@ void ActorSpawner::ProcessFlexBodyWheel(RigDef::FlexBodyWheel & def)
axis_node_closest_to_rigidity_node = ((distance_1 < distance_2)) ? axis_node_1 : axis_node_2;
}

// Tweaks
float override_rim_radius = TuneupDef::getTweakedWheelRimRadius(m_actor->getUsedTuneupEntry(), wheel_id, def.rim_radius);
float override_tire_radius = TuneupDef::getTweakedWheelTireRadius(m_actor->getUsedTuneupEntry(), wheel_id, def.tyre_radius);
std::string override_rim_mesh_name = TuneupDef::getTweakedWheelRimMesh(m_actor->getUsedTuneupEntry(), wheel_id, def.rim_mesh_name);

// Node&beam generation
Ogre::Vector3 axis_vector = axis_node_2->RelPosition - axis_node_1->RelPosition;
wheel.wh_width = axis_vector.length(); // wheel_def.width is ignored.
axis_vector.normalise();
Ogre::Vector3 rim_ray_vector = axis_vector.perpendicular() * def.rim_radius;
Ogre::Vector3 rim_ray_vector = axis_vector.perpendicular() * override_rim_radius;
Ogre::Quaternion rim_ray_rotator = Ogre::Quaternion(Ogre::Degree(-360.f / (def.num_rays * 2)), axis_vector);

// Rim nodes
Expand Down Expand Up @@ -4152,7 +4159,7 @@ void ActorSpawner::ProcessFlexBodyWheel(RigDef::FlexBodyWheel & def)
wheel.wh_rim_nodes[(i * 2) + 1] = & inner_node;
}

Ogre::Vector3 tyre_ray_vector = axis_vector.perpendicular() * def.tyre_radius;
Ogre::Vector3 tyre_ray_vector = axis_vector.perpendicular() * override_tire_radius;
Ogre::Quaternion& tyre_ray_rotator = rim_ray_rotator;
tyre_ray_vector = tyre_ray_rotator * tyre_ray_vector;

Expand Down Expand Up @@ -4284,7 +4291,7 @@ void ActorSpawner::ProcessFlexBodyWheel(RigDef::FlexBodyWheel & def)
// Calculate the point where the support beams get stiff and prevent the tire tread nodes
// bounce into the rim rimradius / tire radius and add 5%, this is a shortbound calc in % !

float support_beams_short_bound = 1.0f - ((def.rim_radius / def.tyre_radius) * 0.95f);
float support_beams_short_bound = 1.0f - ((override_rim_radius / override_tire_radius) * 0.95f);

for (unsigned int i=0; i<def.num_rays; i++)
{
Expand All @@ -4310,8 +4317,8 @@ void ActorSpawner::ProcessFlexBodyWheel(RigDef::FlexBodyWheel & def)
wheel.wh_num_rim_nodes = wheel.wh_num_nodes;
wheel.wh_axis_node_0 = axis_node_1;
wheel.wh_axis_node_1 = axis_node_2;
wheel.wh_radius = def.tyre_radius;
wheel.wh_rim_radius = def.rim_radius;
wheel.wh_radius = override_tire_radius;
wheel.wh_rim_radius = override_rim_radius;
wheel.wh_arm_node = this->GetNodePointer(def.reference_arm_node);

if (def.propulsion != RigDef::WheelPropulsion::NONE)
Expand All @@ -4330,7 +4337,7 @@ void ActorSpawner::ProcessFlexBodyWheel(RigDef::FlexBodyWheel & def)
int wheel_index = m_actor->ar_num_wheels;
++m_actor->ar_num_wheels;

this->CreateFlexBodyWheelVisuals(wheel_index, base_node_index, axis_node_1->pos, axis_node_2->pos, def);
this->CreateFlexBodyWheelVisuals(wheel_index, base_node_index, axis_node_1->pos, axis_node_2->pos, override_rim_radius, override_rim_mesh_name, def);
}

wheel_t::BrakeCombo ActorSpawner::TranslateBrakingDef(RigDef::WheelBraking def)
Expand Down Expand Up @@ -4701,6 +4708,7 @@ void ActorSpawner::BuildWheelBeams(

unsigned int ActorSpawner::AddWheel(RigDef::Wheel & wheel_def)
{
const int wheel_id = m_actor->ar_num_wheels;
unsigned int base_node_index = m_actor->ar_num_nodes;
node_t *axis_node_1 = GetNodePointer(wheel_def.nodes[0]);
node_t *axis_node_2 = GetNodePointer(wheel_def.nodes[1]);
Expand All @@ -4724,16 +4732,19 @@ unsigned int ActorSpawner::AddWheel(RigDef::Wheel & wheel_def)
node_t *swap = axis_node_1;
axis_node_1 = axis_node_2;
axis_node_2 = swap;
}
}

unsigned int wheel_index = BuildWheelObjectAndNodes(
// Tweaks
float override_radius = TuneupDef::getTweakedWheelTireRadius(m_actor->getUsedTuneupEntry(), wheel_id, wheel_def.radius);

BuildWheelObjectAndNodes(
wheel_def.num_rays,
axis_node_1,
axis_node_2,
GetNodePointer(wheel_def.reference_arm_node),
wheel_def.num_rays * 2,
wheel_def.num_rays * 8,
wheel_def.radius,
override_radius,
wheel_def.propulsion,
wheel_def.braking,
wheel_def.node_defaults,
Expand All @@ -4755,17 +4766,17 @@ unsigned int ActorSpawner::AddWheel(RigDef::Wheel & wheel_def)
);

this->CreateWheelVisuals(
wheel_index,
wheel_id,
base_node_index,
wheel_def.num_rays,
wheel_def.face_material_name,
wheel_def.band_material_name,
/*separate_rim:*/false
);

CreateWheelSkidmarks(wheel_index);
CreateWheelSkidmarks(wheel_id);

return wheel_index;
return (unsigned int)wheel_id;
}

void ActorSpawner::CreateWheelSkidmarks(unsigned int wheel_index)
Expand All @@ -4777,6 +4788,7 @@ void ActorSpawner::CreateWheelSkidmarks(unsigned int wheel_index)

unsigned int ActorSpawner::AddWheel2(RigDef::Wheel2 & wheel_2_def)
{
const int wheel_id = m_actor->ar_num_wheels;
unsigned int base_node_index = m_actor->ar_num_nodes;
wheel_t & wheel = m_actor->ar_wheels[m_actor->ar_num_wheels];
node_t *axis_node_1 = GetNodePointer(wheel_2_def.nodes[0]);
Expand Down Expand Up @@ -4813,11 +4825,14 @@ unsigned int ActorSpawner::AddWheel2(RigDef::Wheel2 & wheel_2_def)
rigidity_beam_side_1 = distance_1 < distance_2;
}

// Tweaks
float override_rim_radius = TuneupDef::getTweakedWheelRimRadius(m_actor->getUsedTuneupEntry(), wheel_id, override_rim_radius);
float override_tire_radius = TuneupDef::getTweakedWheelTireRadius(m_actor->getUsedTuneupEntry(), wheel_id, override_tire_radius);

/* Node&beam generation */
Ogre::Vector3 axis_vector = axis_node_2->RelPosition - axis_node_1->RelPosition;
axis_vector.normalise();
Ogre::Vector3 rim_ray_vector = Ogre::Vector3(0, wheel_2_def.rim_radius, 0);
Ogre::Vector3 rim_ray_vector = Ogre::Vector3(0, override_rim_radius, 0);
Ogre::Quaternion rim_ray_rotator = Ogre::Quaternion(Ogre::Degree(-360.f / wheel_2_def.num_rays), axis_vector);

/* Width */
Expand Down Expand Up @@ -4859,7 +4874,7 @@ unsigned int ActorSpawner::AddWheel2(RigDef::Wheel2 & wheel_2_def)
rim_ray_vector = rim_ray_rotator * rim_ray_vector;
}

Ogre::Vector3 tyre_ray_vector = Ogre::Vector3(0, wheel_2_def.tyre_radius, 0);
Ogre::Vector3 tyre_ray_vector = Ogre::Vector3(0, override_tire_radius, 0);
Ogre::Quaternion tyre_ray_rotator = Ogre::Quaternion(Ogre::Degree(-180.f / wheel_2_def.num_rays), axis_vector);
tyre_ray_vector = tyre_ray_rotator * tyre_ray_vector;

Expand Down Expand Up @@ -4977,8 +4992,8 @@ unsigned int ActorSpawner::AddWheel2(RigDef::Wheel2 & wheel_2_def)
wheel.wh_num_rim_nodes = wheel.wh_num_nodes;
wheel.wh_axis_node_0 = axis_node_1;
wheel.wh_axis_node_1 = axis_node_2;
wheel.wh_radius = wheel_2_def.tyre_radius;
wheel.wh_rim_radius = wheel_2_def.rim_radius;
wheel.wh_radius = override_tire_radius;
wheel.wh_rim_radius = override_rim_radius;
wheel.wh_arm_node = this->GetNodePointer(wheel_2_def.reference_arm_node);

if (wheel_2_def.propulsion != RigDef::WheelPropulsion::NONE)
Expand Down Expand Up @@ -5053,6 +5068,8 @@ void ActorSpawner::CreateFlexBodyWheelVisuals(
unsigned int node_base_index,
NodeNum_t axis_node_1,
NodeNum_t axis_node_2,
float override_radius,
std::string override_mesh_name,
RigDef::FlexBodyWheel& def)
{
m_actor->GetGfxActor()->UpdateSimDataBuffer(); // fill all current nodes - needed to setup flexing meshes
Expand All @@ -5063,9 +5080,9 @@ void ActorSpawner::CreateFlexBodyWheelVisuals(
axis_node_1,
axis_node_2,
def.num_rays,
def.rim_mesh_name,
override_mesh_name,
"tracks/trans", // Rim material name. Original parser: was hardcoded in BTS_FLEXBODYWHEELS
def.rim_radius,
override_radius,
def.side != RigDef::WheelSide::RIGHT
);

Expand Down Expand Up @@ -5806,7 +5823,10 @@ void ActorSpawner::ProcessNode(RigDef::Node & def)
node.pos = inserted_node.first; /* Node index */

/* Positioning */
Ogre::Vector3 node_position = m_spawn_position + def.position;
Ogre::Vector3 node_position = m_spawn_position + TuneupDef::getTweakedNodePosition(m_actor->getUsedTuneupEntry(), node.pos, def.position);
ROR_ASSERT(!isnan(node_position.x));
ROR_ASSERT(!isnan(node_position.y));
ROR_ASSERT(!isnan(node_position.z));
node.AbsPosition = node_position;
node.RelPosition = node_position - m_actor->ar_origin;

Expand Down
2 changes: 2 additions & 0 deletions source/main/physics/ActorSpawner.h
Original file line number Diff line number Diff line change
Expand Up @@ -402,6 +402,8 @@ class ActorSpawner
unsigned int node_base_index,
NodeNum_t axis_node_1,
NodeNum_t axis_node_2,
float override_radius,
std::string override_mesh_name,
RigDef::FlexBodyWheel& def);

void BuildMeshWheelVisuals(
Expand Down
17 changes: 11 additions & 6 deletions source/main/resources/CacheSystem.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1718,36 +1718,41 @@ void CacheSystem::ModifyProject(ModifyProjectRequest* request)
tuneup_entry->tuneup_def->remove_props = save_entry->tuneup_def->remove_props;
tuneup_entry->tuneup_def->use_addonparts.clear();
tuneup_entry->tuneup_def->use_addonparts = save_entry->tuneup_def->use_addonparts;
tuneup_entry->tuneup_def->wheel_tweaks.clear();
tuneup_entry->tuneup_def->wheel_tweaks = save_entry->tuneup_def->wheel_tweaks;
tuneup_entry->tuneup_def->node_tweaks.clear();
tuneup_entry->tuneup_def->node_tweaks = save_entry->tuneup_def->node_tweaks;
break;
}

case ModifyProjectRequestType::PROJECT_RESET_TUNEUP:
tuneup_entry->tuneup_def->remove_flexbodies.clear();
tuneup_entry->tuneup_def->remove_props.clear();
tuneup_entry->tuneup_def->use_addonparts.clear();
tuneup_entry->tuneup_def->wheel_tweaks.clear();
tuneup_entry->tuneup_def->node_tweaks.clear();
break;

default:
break;
}


// resolve unwanted elements
for (const std::string& addonpart_file: tuneup_entry->tuneup_def->use_addonparts)
// resolve unwanted+tweaked elements
/* for (const std::string& addonpart_file: tuneup_entry->tuneup_def->use_addonparts)
{
CacheEntryPtr addonpart_entry = this->FindEntryByFilename(LT_AddonPart, /*partial:*/false, addonpart_file);
CacheEntryPtr addonpart_entry = this->FindEntryByFilename(LT_AddonPart, false, addonpart_file);
if (addonpart_entry)
{
this->LoadResource(addonpart_entry);
AddonPartUtility util;
util.ResolveUnwantedElements(tuneup_entry->tuneup_def, addonpart_entry);
util.ResolveUnwantedAndTweakedElements(tuneup_entry->tuneup_def, addonpart_entry);
}
else
{
App::GetConsole()->putMessage(Console::CONSOLE_MSGTYPE_INFO, Console::CONSOLE_SYSTEM_WARNING,
fmt::format(_LC("CacheSystem", "Problem evaluating unwanted parts - addonpart '{}' not found in cache"), addonpart_file));
}
}
}*/

// Update the .tuneup file (rembember this is the 'working' aka 'autogenerated' tuneup)
Ogre::DataStreamPtr datastream = Ogre::ResourceGroupManager::getSingleton().createResource(tuneup_entry->fname, tuneup_entry->resource_group, /*overwrite:*/true);
Expand Down
Loading

0 comments on commit d7f313a

Please sign in to comment.