Files
FluidSimCpp/tests/mesh_resolution_tests.cpp

48 lines
2.9 KiB
C++

#include "FluidSim/DesktopScenario.hpp"
#include <atomic>
#include <cmath>
#include <iostream>
#include <limits>
#include <stdexcept>
#include <thread>
using namespace fluidsim::port;
void check(bool value,const char* reason) {if(!value)throw std::runtime_error(reason);}
double volume(const ScenarioSnapshot& s) {
double sum=0;
for(int p=0;p<32;++p) for(std::size_t i=0;i<s.pipe_areas[p].size();++i)
sum+=double(s.pipe_areas[p][i])*s.pipe_lengths[p][i];
return sum;
}
int main() {
try {
check(mesh_cell_count(.1f,100)==10,"decimal cell count rounded upward");
for(const auto& example:scenario_examples())
check((example.kind==ScenarioKind::TwoStroke?example.two.cells_per_meter:example.engine.cells_per_meter)>0,"scenario lacks mesh density");
for(const auto* id:{"single-450","yz-racing","saab-chambered"}) {
DesktopScenario scenario(scenario_example(id));
scenario.set_controls(.3f,.1f,.6f);scenario.set_pipe_solver(PipeSolver::Hllc);scenario.set_audio_scene(OutdoorScene::Dry);
const double original_volume=volume(scenario.snapshot());
std::atomic<bool> finite{true};
std::jthread worker([&]{for(int i=0;i<2048;++i) {const auto f=scenario.process();if(!std::isfinite(f.left)||!std::isfinite(f.right))finite=false;}});
scenario.set_cells_per_meter(35);
worker.join();check(finite,"concurrent resolution rebuild corrupted audio");
auto state=scenario.snapshot();
check(state.cells_per_meter==35 && state.pipe_solver==PipeSolver::Hllc && state.audio_scene==OutdoorScene::Dry,"resolution rebuild lost options");
check(std::abs(volume(state)-original_volume)<original_volume*1e-5,"remeshing changed pipe volume");
for(const auto& lengths:state.pipe_lengths) for(float length:lengths)
check(length<=1.f/35+1e-6f,"profile or uniform pipe ignored cells/m");
check(std::abs(state.clutch-.6f)<1e-5f,"resolution rebuild lost controls");
const auto old_count=state.pipe_states[0].size();
for(float invalid:{0.f,-1.f,501.f,std::numeric_limits<float>::quiet_NaN()}) {
bool rejected=false;try{scenario.set_cells_per_meter(invalid);}catch(const std::exception&){rejected=true;}
check(rejected,"invalid density accepted");
check(scenario.snapshot().pipe_states[0].size()==old_count,"failed rebuild changed live mesh");
}
}
DesktopScenario a(scenario_example("single-450")),b(scenario_example("single-650"));
const float density=b.snapshot().cells_per_meter;a.set_cells_per_meter(50);
check(b.snapshot().cells_per_meter==density,"resolution leaked between scenarios");
std::cout<<"Uniform/profile mesh resolution, volume, rebuild, isolation and validation checks passed\n";
} catch(const std::exception& e) {std::cerr<<e.what()<<'\n';return 1;}
}