16
0
mirror of https://github.com/MaSzyna-EU07/maszyna.git synced 2026-07-22 22:09:19 +02:00

load visualization submodel visibility selection tweak, passenger train acceleration ai logic enhancement, brake code enhancement, cab control label tweak

This commit is contained in:
tmj-fstate
2020-06-05 16:43:07 +02:00
parent 203cefac8d
commit ad1a14082c
8 changed files with 65 additions and 76 deletions

View File

@@ -153,6 +153,8 @@ const double EasyReactionTime = 0.5; //[s] przebłyski świadomości dla zwykłe
const double HardReactionTime = 0.2; const double HardReactionTime = 0.2;
const double EasyAcceleration = 0.85; //[m/ss] const double EasyAcceleration = 0.85; //[m/ss]
const double HardAcceleration = 9.81; const double HardAcceleration = 9.81;
const double PassengetTrainAcceleration = 0.40;
const double HeavyPassengetTrainAcceleration = 0.20;
const double CargoTrainAcceleration = 0.25; const double CargoTrainAcceleration = 0.25;
const double HeavyCargoTrainAcceleration = 0.10; const double HeavyCargoTrainAcceleration = 0.10;
const double PrepareTime = 2.0; //[s] przebłyski świadomości przy odpalaniu const double PrepareTime = 2.0; //[s] przebłyski świadomości przy odpalaniu
@@ -2065,6 +2067,7 @@ void TController::AutoRewident()
fBrake_a1[i+1] /= (12*fMass); fBrake_a1[i+1] /= (12*fMass);
} }
IsPassengerTrain = ( mvOccupied->CategoryFlag == 1 ) && ( mvOccupied->TrainType != dt_EZT ) && ( mvOccupied->TrainType != dt_DMU ) && ( ( mvOccupied->BrakeDelayFlag & bdelay_G ) == 0 );
IsCargoTrain = ( mvOccupied->CategoryFlag == 1 ) && ( ( mvOccupied->BrakeDelayFlag & bdelay_G ) != 0 ); IsCargoTrain = ( mvOccupied->CategoryFlag == 1 ) && ( ( mvOccupied->BrakeDelayFlag & bdelay_G ) != 0 );
IsHeavyCargoTrain = ( true == IsCargoTrain ) && ( fBrake_a0[ 1 ] > 0.4 ) && ( iVehicles - ControlledEnginesCount > 0 ) && ( fMass / iVehicles > 50000 ); IsHeavyCargoTrain = ( true == IsCargoTrain ) && ( fBrake_a0[ 1 ] > 0.4 ) && ( iVehicles - ControlledEnginesCount > 0 ) && ( fMass / iVehicles > 50000 );
@@ -6235,6 +6238,9 @@ TController::UpdateSituation(double dt) {
} }
// HACK: limit acceleration for cargo trains, to reduce probability of breaking couplers on sudden jolts // HACK: limit acceleration for cargo trains, to reduce probability of breaking couplers on sudden jolts
// TBD: expand this behaviour to all trains with car(s) exceeding certain weight? // TBD: expand this behaviour to all trains with car(s) exceeding certain weight?
if( ( IsPassengerTrain ) && ( iVehicles - ControlledEnginesCount > 0 ) ) {
AccDesired = std::min( AccDesired, ( iVehicles - ControlledEnginesCount > 8 ? HeavyPassengetTrainAcceleration : PassengetTrainAcceleration ) );
}
if( ( IsCargoTrain ) && ( iVehicles - ControlledEnginesCount > 0 ) ) { if( ( IsCargoTrain ) && ( iVehicles - ControlledEnginesCount > 0 ) ) {
AccDesired = std::min( AccDesired, CargoTrainAcceleration ); AccDesired = std::min( AccDesired, CargoTrainAcceleration );
} }

View File

@@ -472,6 +472,7 @@ private:
int iVehicles = 0; // ilość pojazdów w składzie int iVehicles = 0; // ilość pojazdów w składzie
int ControlledEnginesCount{ 0 }; // number of powered vehicles under driver's control int ControlledEnginesCount{ 0 }; // number of powered vehicles under driver's control
bool iEngineActive{ false }; // ABu: Czy silnik byl juz zalaczony bool iEngineActive{ false }; // ABu: Czy silnik byl juz zalaczony
bool IsPassengerTrain{ false };
bool IsCargoTrain{ false }; bool IsCargoTrain{ false };
bool IsHeavyCargoTrain{ false }; bool IsHeavyCargoTrain{ false };
double fReady = 0.0; // poziom odhamowania wagonów double fReady = 0.0; // poziom odhamowania wagonów

View File

@@ -686,7 +686,7 @@ TDynamicObject::toggle_lights() {
( sectionname.find( "compartment" ) == 0 ) ( sectionname.find( "compartment" ) == 0 )
|| ( sectionname.find( "przedzial" ) == 0 ) ) { || ( sectionname.find( "przedzial" ) == 0 ) ) {
// compartments are lit with 75% probability // compartments are lit with 75% probability
section.light_level = ( Random() < 0.75 ? 0.75f : 0.15f ); section.light_level = ( Random() < 0.75 ? 0.75f : 0.10f );
} }
} }
SectionLightsActive = true; SectionLightsActive = true;
@@ -1119,21 +1119,22 @@ void TDynamicObject::ABuLittleUpdate(double ObjSqrDist)
} }
} }
// load chunks visibility // load chunks visibility
for( auto const &section : SectionLoadVisibility ) { for( auto const &section : Sections ) {
section.submodel->iVisible = section.visible; // section isn't guaranteed to have load model, so check that first
if( false == section.visible ) { if( section.load == nullptr ) { continue; }
section.load->iVisible = ( section.load_chunks_visible > 0 );
// if the section root isn't visible we can skip meddling with its children // if the section root isn't visible we can skip meddling with its children
continue; if( false == section.load->iVisible ) { continue; }
}
// if the section root is visible set the state of section chunks // if the section root is visible set the state of section chunks
auto *sectionchunk { section.submodel->ChildGet() }; auto *sectionchunk { section.load->ChildGet() };
auto visiblechunkcount { section.visible_chunks }; auto visiblechunkcount { section.load_chunks_visible };
while( sectionchunk != nullptr ) { while( sectionchunk != nullptr ) {
sectionchunk->iVisible = ( visiblechunkcount > 0 ); sectionchunk->iVisible = ( visiblechunkcount > 0 );
--visiblechunkcount; --visiblechunkcount;
sectionchunk = sectionchunk->NextGet(); sectionchunk = sectionchunk->NextGet();
} }
} }
// driver cabs visibility // driver cabs visibility
for( int cabidx = 0; cabidx < LowPolyIntCabs.size(); ++cabidx ) { for( int cabidx = 0; cabidx < LowPolyIntCabs.size(); ++cabidx ) {
if( LowPolyIntCabs[ cabidx ] == nullptr ) { continue; } if( LowPolyIntCabs[ cabidx ] == nullptr ) { continue; }
@@ -2136,15 +2137,15 @@ TDynamicObject::Init(std::string Name, // nazwa pojazdu, np. "EU07-424"
// TODO: definition of relevant compartments in the .mmd file // TODO: definition of relevant compartments in the .mmd file
TSubModel *submodel { nullptr }; TSubModel *submodel { nullptr };
if( ( submodel = mdLowPolyInt->GetFromName( "cab0" ) ) != nullptr ) { if( ( submodel = mdLowPolyInt->GetFromName( "cab0" ) ) != nullptr ) {
Sections.push_back( { submodel, nullptr, 0.0f } ); Sections.push_back( { submodel, nullptr, 0, 0.0f } );
LowPolyIntCabs[ 0 ] = submodel; LowPolyIntCabs[ 0 ] = submodel;
} }
if( ( submodel = mdLowPolyInt->GetFromName( "cab1" ) ) != nullptr ) { if( ( submodel = mdLowPolyInt->GetFromName( "cab1" ) ) != nullptr ) {
Sections.push_back( { submodel, nullptr, 0.0f } ); Sections.push_back( { submodel, nullptr, 0, 0.0f } );
LowPolyIntCabs[ 1 ] = submodel; LowPolyIntCabs[ 1 ] = submodel;
} }
if( ( submodel = mdLowPolyInt->GetFromName( "cab2" ) ) != nullptr ) { if( ( submodel = mdLowPolyInt->GetFromName( "cab2" ) ) != nullptr ) {
Sections.push_back( { submodel, nullptr, 0.0f } ); Sections.push_back( { submodel, nullptr, 0, 0.0f } );
LowPolyIntCabs[ 2 ] = submodel; LowPolyIntCabs[ 2 ] = submodel;
} }
// passenger car compartments // passenger car compartments
@@ -2280,6 +2281,7 @@ TDynamicObject::init_sections( TModel3d const *Model, std::string const &Namepre
Sections.push_back( { Sections.push_back( {
sectionsubmodel, sectionsubmodel,
nullptr, // pointers to load sections are generated afterwards nullptr, // pointers to load sections are generated afterwards
0,
0.0f } ); 0.0f } );
++sectioncount; ++sectioncount;
} }
@@ -2723,58 +2725,49 @@ void TDynamicObject::LoadUpdate() {
void void
TDynamicObject::update_load_sections() { TDynamicObject::update_load_sections() {
SectionLoadVisibility.clear(); SectionLoadOrder.clear();
for( auto &section : Sections ) { for( auto &section : Sections ) {
section.load = GetSubmodelFromName( mdLoad, section.compartment->pName ); section.load = GetSubmodelFromName( mdLoad, section.compartment->pName );
if( ( section.load != nullptr ) if( section.load != nullptr ) {
&& ( section.load->count_children() > 0 ) ) { // create entry for each load model chunk assigned to the section
SectionLoadVisibility.push_back( { section.load, false } ); // TBD, TODO: store also pointer to chunk submodel and control its visibility more directly, instead of per-section visibility flag?
auto loadchunkcount { section.load->count_children() };
while( loadchunkcount-- ) {
SectionLoadOrder.push_back( &section );
}
// HACK: disable automatic self-illumination threshold, at least until 3d model update // HACK: disable automatic self-illumination threshold, at least until 3d model update
if( MoverParameters->CompartmentLights.start_type == start_t::manual ) { if( MoverParameters->CompartmentLights.start_type == start_t::manual ) {
section.load->SetSelfIllum( 2.0f, true, false ); section.load->SetSelfIllum( 2.0f, true, false );
} }
} }
} }
shuffle_load_sections(); shuffle_load_order();
} }
void void
TDynamicObject::update_load_visibility() { TDynamicObject::update_load_visibility() {
/* // start with clean load chunk visibility slate
if( Random() < 0.25 ) { for( auto &section : Sections ) {
shuffle_load_sections(); section.load_chunks_visible = 0;
} }
*/ // each entry in load order sequence matches a single chunk of the section it points to
auto loadpercentage { ( // the length of load order sequence matches total number of load chunks
auto const loadpercentage { (
MoverParameters->MaxLoad == 0.f ? MoverParameters->MaxLoad == 0.f ?
0.0 : 0.0 :
100.0 * MoverParameters->LoadAmount / MoverParameters->MaxLoad ) }; MoverParameters->LoadAmount / MoverParameters->MaxLoad ) };
auto const sectionloadpercentage { ( auto visiblechunkcount { (
SectionLoadVisibility.empty() ? SectionLoadOrder.empty() ?
0.0 : 0 :
100.0 / SectionLoadVisibility.size() ) }; static_cast<int>( std::ceil( loadpercentage * SectionLoadOrder.size() ) ) ) };
// set as many sections as we can, given overall load percentage and how much of full percentage is covered by each chunk for( auto *section : SectionLoadOrder ) {
std::for_each( if( visiblechunkcount == 0 ) { break; }
std::begin( SectionLoadVisibility ), std::end( SectionLoadVisibility ), section->load_chunks_visible++;
[&]( section_visibility &section ) { --visiblechunkcount;
section.visible = ( loadpercentage > 0.0 );
section.visible_chunks = 0;
auto const sectionchunkcount { section.submodel->count_children() };
auto const sectionchunkloadpercentage{ (
sectionchunkcount == 0 ?
0.0 :
sectionloadpercentage / sectionchunkcount ) };
auto *sectionchunk { section.submodel->ChildGet() };
while( sectionchunk != nullptr ) {
if( loadpercentage > 0.0 ) {
++section.visible_chunks;
loadpercentage -= sectionchunkloadpercentage;
} }
sectionchunk = sectionchunk->NextGet();
} } );
} }
void void
@@ -2791,16 +2784,16 @@ TDynamicObject::update_load_offset() {
} }
void void
TDynamicObject::shuffle_load_sections() { TDynamicObject::shuffle_load_order() {
std::shuffle( std::begin( SectionLoadVisibility ), std::end( SectionLoadVisibility ), Global.random_engine ); std::shuffle( std::begin( SectionLoadOrder ), std::end( SectionLoadOrder ), Global.random_engine );
// shift chunks assigned to corridors to the end of the list, so they show up last // shift chunks assigned to corridors to the end of the list, so they show up last
std::stable_partition( std::stable_partition(
std::begin( SectionLoadVisibility ), std::end( SectionLoadVisibility ), std::begin( SectionLoadOrder ), std::end( SectionLoadOrder ),
[]( section_visibility const &section ) { []( vehicle_section const *section ) {
return ( return (
( section.submodel->pName.find( "compartment" ) == 0 ) ( section->compartment->pName.find( "compartment" ) == 0 )
|| ( section.submodel->pName.find( "przedzial" ) == 0 ) ); } ); || ( section->compartment->pName.find( "przedzial" ) == 0 ) ); } );
// NOTE: potentially we're left with a mix of corridor and external section loads // NOTE: potentially we're left with a mix of corridor and external section loads
// but that's not necessarily a wrong outcome, so we leave it this way for the time being // but that's not necessarily a wrong outcome, so we leave it this way for the time being
} }

View File

@@ -230,16 +230,12 @@ public:
struct vehicle_section { struct vehicle_section {
TSubModel *compartment; TSubModel *compartment;
TSubModel *load; TSubModel *load;
int load_chunks_visible;
float light_level; float light_level;
}; };
std::vector<vehicle_section> Sections; // table of recognized vehicle sections std::vector<vehicle_section> Sections; // table of recognized vehicle sections
bool SectionLightsActive { false }; // flag indicating whether section lights were set. bool SectionLightsActive { false }; // flag indicating whether section lights were set.
struct section_visibility { std::vector<vehicle_section *> SectionLoadOrder; // helper, activation/deactivation load chunk sequence
TSubModel *submodel;
bool visible;
int visible_chunks;
};
std::vector<section_visibility> SectionLoadVisibility; // visibility of specific sections of the load 3d model
private: private:
// zmienne i metody do animacji submodeli; Ra: sprzatam animacje w pojeździe // zmienne i metody do animacji submodeli; Ra: sprzatam animacje w pojeździe
@@ -574,7 +570,7 @@ private:
void update_load_sections(); void update_load_sections();
void update_load_visibility(); void update_load_visibility();
void update_load_offset(); void update_load_offset();
void shuffle_load_sections(); void shuffle_load_order();
void update_destinations(); void update_destinations();
bool Update(double dt, double dt1); bool Update(double dt, double dt1);
bool FastUpdate(double dt); bool FastUpdate(double dt);

View File

@@ -10994,7 +10994,6 @@ bool TMoverParameters::CheckLocomotiveParameters(bool ReadyFlag, int Dir)
WriteLog( "XBT EStED" ); WriteLog( "XBT EStED" );
Hamulec = std::make_shared<TEStED>( MaxBrakePress[ 3 ], BrakeCylRadius, BrakeCylDist, BrakeVVolume, BrakeCylNo, BrakeDelays, BrakeMethod, NAxles, NBpA ); Hamulec = std::make_shared<TEStED>( MaxBrakePress[ 3 ], BrakeCylRadius, BrakeCylDist, BrakeVVolume, BrakeCylNo, BrakeDelays, BrakeMethod, NAxles, NBpA );
Hamulec->SetRM( RapidMult ); Hamulec->SetRM( RapidMult );
Hamulec->SetRV( RapidVel );
if( MBPM < 2 ) { if( MBPM < 2 ) {
//jesli przystawka wazaca //jesli przystawka wazaca
Hamulec->SetLP( 0, MaxBrakePress[ 3 ], 0 ); Hamulec->SetLP( 0, MaxBrakePress[ 3 ], 0 );
@@ -11017,7 +11016,6 @@ bool TMoverParameters::CheckLocomotiveParameters(bool ReadyFlag, int Dir)
Hamulec = std::make_shared<TEStEP1>(MaxBrakePress[3], BrakeCylRadius, BrakeCylDist, BrakeVVolume, BrakeCylNo, BrakeDelays, BrakeMethod, NAxles, NBpA); Hamulec = std::make_shared<TEStEP1>(MaxBrakePress[3], BrakeCylRadius, BrakeCylDist, BrakeVVolume, BrakeCylNo, BrakeDelays, BrakeMethod, NAxles, NBpA);
Hamulec->SetLP( Mass, MBPM, MaxBrakePress[1] ); Hamulec->SetLP( Mass, MBPM, MaxBrakePress[1] );
Hamulec->SetRM( RapidMult ); Hamulec->SetRM( RapidMult );
Hamulec->SetRV( RapidVel );
break; break;
} }
case TBrakeValve::CV1: case TBrakeValve::CV1:
@@ -11037,6 +11035,7 @@ bool TMoverParameters::CheckLocomotiveParameters(bool ReadyFlag, int Dir)
} }
Hamulec->SetASBP( MaxBrakePress[ 4 ] ); Hamulec->SetASBP( MaxBrakePress[ 4 ] );
Hamulec->SetRV( RapidVel );
switch( BrakeHandle ) { switch( BrakeHandle ) {
case TBrakeHandle::FV4a: case TBrakeHandle::FV4a:

View File

@@ -1685,11 +1685,6 @@ void TEStED::SetLP( double const TM, double const LM, double const TBP )
TareBP = TBP; TareBP = TBP;
} }
void TEStED::SetRV(double const RVR)
{
RV = RVR;
}
//---DAKO CV1--- //---DAKO CV1---
void TCV1::CheckState( double const BCP, double &dV1 ) void TCV1::CheckState( double const BCP, double &dV1 )
@@ -2137,13 +2132,13 @@ double TKE::GetPF( double const PP, double const dt, double const Vel )
if (!((typeid(*FM) == typeid(TDisk1)) || if (!((typeid(*FM) == typeid(TDisk1)) ||
(typeid(*FM) == typeid(TDisk2)))) // jesli zeliwo to schodz (typeid(*FM) == typeid(TDisk2)))) // jesli zeliwo to schodz
RapidStatus = ((BrakeDelayFlag & bdelay_R) == bdelay_R) && RapidStatus = ((BrakeDelayFlag & bdelay_R) == bdelay_R) &&
(((Vel > 50) && (RapidStatus)) || (Vel > 70)); ((RV < 0) || ((Vel > RV) && (RapidStatus)) || (Vel > (RV + 20)));
else // jesli tarczowki, to zostan else // jesli tarczowki, to zostan
RapidStatus = ((BrakeDelayFlag & bdelay_R) == bdelay_R); RapidStatus = ((BrakeDelayFlag & bdelay_R) == bdelay_R);
// temp:=1.9-0.9*int(RapidStatus); // temp:=1.9-0.9*int(RapidStatus);
if ((RM * RM > 0.1)) // jesli jest rapid if ((RM * RM > 0.001)) // jesli jest rapid
if ((RM > 0)) // jesli dodatni (naddatek); if ((RM > 0)) // jesli dodatni (naddatek);
temp = 1 - RM * int(RapidStatus); temp = 1 - RM * int(RapidStatus);
else else

View File

@@ -192,8 +192,9 @@ class TBrake {
double SizeBC = 0.0; //rozmiar^2 CH (w stosunku do 14") double SizeBC = 0.0; //rozmiar^2 CH (w stosunku do 14")
bool DCV = false; //podwojny zawor zwrotny bool DCV = false; //podwojny zawor zwrotny
double ASBP = 0.0; //cisnienie hamulca pp double ASBP = 0.0; //cisnienie hamulca pp
int UniversalFlag = 0; //flaga wcisnietych przyciskow uniwersalnych double RV = 0.0; // rapid activation vehicle velocity threshold
int UniversalFlag = 0; //flaga wcisnietych przyciskow uniwersalnych
int BrakeStatus{ b_off }; //flaga stanu int BrakeStatus{ b_off }; //flaga stanu
int SoundFlag = 0; int SoundFlag = 0;
@@ -216,7 +217,7 @@ class TBrake {
bool Releaser() const; bool Releaser() const;
virtual void SetEPS( double const nEPS ); //hamulec EP virtual void SetEPS( double const nEPS ); //hamulec EP
virtual void SetRM( double const RMR ) {}; //ustalenie przelozenia rapida virtual void SetRM( double const RMR ) {}; //ustalenie przelozenia rapida
virtual void SetRV( double const RVR) {}; //ustalenie przelozenia rapida virtual void SetRV( double const RVR ) { RV = RVR; }; //ustalenie przelozenia rapida
virtual void SetLP(double const TM, double const LM, double const TBP) {}; //parametry przystawki wazacej virtual void SetLP(double const TM, double const LM, double const TBP) {}; //parametry przystawki wazacej
virtual void SetLBP(double const P) {}; //cisnienie z hamulca pomocniczego virtual void SetLBP(double const P) {}; //cisnienie z hamulca pomocniczego
virtual void PLC(double const mass) {}; //wspolczynnik cisnienia przystawki wazacej virtual void PLC(double const mass) {}; //wspolczynnik cisnienia przystawki wazacej
@@ -347,7 +348,6 @@ class TLSt : public TESt4R {
protected: protected:
double LBP = 0.0; //cisnienie hamulca pomocniczego double LBP = 0.0; //cisnienie hamulca pomocniczego
double RM = 0.0; //przelozenie rapida double RM = 0.0; //przelozenie rapida
double RV = 0.0;
double EDFlag = 0.0; //luzowanie hamulca z powodu zalaczonego ED double EDFlag = 0.0; //luzowanie hamulca z powodu zalaczonego ED
public: public:
@@ -383,7 +383,6 @@ class TEStED : public TLSt { //zawor z EP09 - Est4 z oddzielnym przekladnikiem,
double GetEDBCP()/*override*/; //cisnienie tylko z hamulca zasadniczego, uzywane do hamulca ED double GetEDBCP()/*override*/; //cisnienie tylko z hamulca zasadniczego, uzywane do hamulca ED
void PLC(double const mass); //wspolczynnik cisnienia przystawki wazacej void PLC(double const mass); //wspolczynnik cisnienia przystawki wazacej
void SetLP( double const TM, double const LM, double const TBP ); //parametry przystawki wazacej void SetLP( double const TM, double const LM, double const TBP ); //parametry przystawki wazacej
void SetRV(double const RVR); //ustalenie predkosci przelaczenia rapida
inline TEStED(double i_mbp, double i_bcr, double i_bcd, double i_brc, int i_bcn, int i_BD, int i_mat, int i_ba, int i_nbpa) : inline TEStED(double i_mbp, double i_bcr, double i_bcd, double i_brc, int i_bcn, int i_BD, int i_mat, int i_ba, int i_nbpa) :
TLSt( i_mbp, i_bcr, i_bcd, i_brc, i_bcn, i_BD, i_mat, i_ba, i_nbpa) TLSt( i_mbp, i_bcr, i_bcd, i_brc, i_bcn, i_BD, i_mat, i_ba, i_nbpa)

View File

@@ -166,10 +166,10 @@ init() {
"right marker light", "right marker light",
"light pattern", "light pattern",
"rear upper headlight", "rear upper headlight",
"rear left headlight",
"rear right headlight", "rear right headlight",
"rear left marker light", "rear left headlight",
"rear right marker light", "rear right marker light",
"rear left marker light",
"compressor", "compressor",
"local compressor", "local compressor",
"converter", "converter",
@@ -368,10 +368,10 @@ init() {
"sygnal prawy", "sygnal prawy",
"programator swiatel", "programator swiatel",
"tylny reflektor gorny", "tylny reflektor gorny",
"tylny reflektor lewy",
"tylny reflektor prawy", "tylny reflektor prawy",
"tylny sygnal lewy", "tylny reflektor lewy",
"tylny sygnal prawy", "tylny sygnal prawy",
"tylny sygnal lewy",
"sprezarka", "sprezarka",
"sprezarka lokalna", "sprezarka lokalna",
"przetwornica", "przetwornica",