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

build 180202. tga texture origin bit recognition, audio file load failure crash fix, cab controls positioning fix,

This commit is contained in:
tmj-fstate
2018-02-02 15:49:13 +01:00
parent 23761dc665
commit b3e7b88bbc
11 changed files with 115 additions and 131 deletions

View File

@@ -105,7 +105,7 @@ TButton::model_offset() const {
return (
submodel != nullptr ?
submodel->offset( 2.5f ) :
submodel->offset( std::numeric_limits<float>::max() ) :
glm::vec3() );
}

View File

@@ -5875,16 +5875,14 @@ TDynamicObject::powertrain_sounds::render( TMoverParameters const &Vehicle, doub
}
}
if( Vehicle.TrainType == dt_ET40 ) {
if( Vehicle.Vel > 0.1 ) {
transmission
.pitch( transmission.m_frequencyoffset + transmission.m_frequencyfactor * Vehicle.Vel )
.gain( transmission.m_amplitudeoffset + transmission.m_amplitudefactor * Vehicle.Vel )
.play( sound_flags::exclusive | sound_flags::looping );
}
else {
transmission.stop();
}
if( Vehicle.Vel > 0.1 ) {
transmission
.pitch( transmission.m_frequencyoffset + transmission.m_frequencyfactor * Vehicle.Vel )
.gain( transmission.m_amplitudeoffset + transmission.m_amplitudefactor * Vehicle.Vel )
.play( sound_flags::exclusive | sound_flags::looping );
}
else {
transmission.stop();
}
}

View File

@@ -72,8 +72,8 @@ struct global_settings {
GLfloat FogColor[ 3 ] = { 0.6f, 0.7f, 0.8f };
double fFogStart{ 1700 };
double fFogEnd{ 2000 };
std::string Season; // season of the year, based on simulation date
std::string Weather{ "clear:" }; // current weather
std::string Season{}; // season of the year, based on simulation date
std::string Weather{ "cloudy:" }; // current weather
bool FullPhysics{ true }; // full calculations performed for each simulation step
bool bnewAirCouplers{ true };
double fMoveLight{ -1 }; // numer dnia w roku albo -1

View File

@@ -1187,7 +1187,8 @@ TSubModel::offset( float const Geometrytestoffsetthreshold ) const {
if( true == TestFlag( iFlags, 0x0200 ) ) {
// flip coordinates for t3d file which wasn't yet initialized
if( std::abs( offset.y ) > offset.z ) {
if( ( false == Global.pWorld->InitPerformed() )
|| ( false == Vertices.empty() ) ) {
// NOTE, HACK: results require flipping if the model wasn't yet initialized, so we're using crude method to detect possible cases
// TODO: sort out this mess, either unify offset lookups to take place before (or after) initialization,
// or provide way to determine on submodel level whether the initialization took place

View File

@@ -484,6 +484,12 @@ opengl_texture::load_TGA() {
return;
}
if( ( tgaheader[ 17 ] & 0x20 ) != 0 ) {
// normally origin is bottom-left
// if byte 17 bit 5 is set, it is top-left and needs flip
flip_vertical();
}
downsize( GL_BGRA );
if( ( data_width > Global.iMaxTextureSize ) || ( data_height > Global.iMaxTextureSize ) ) {
// for non-square textures there's currently possibility the scaling routine will have to abort
@@ -702,6 +708,21 @@ opengl_texture::downsize( GLuint const Format ) {
};
}
void
opengl_texture::flip_vertical() {
auto const swapsize { data_width * 4 };
auto destination { data.begin() + ( data_height - 1 ) * swapsize };
auto sampler { data.begin() };
for( auto row = 0; row < data_height / 2; ++row ) {
std::swap_ranges( sampler, sampler + swapsize, destination );
sampler += swapsize;
destination -= swapsize;
}
}
void
texture_manager::assign_units( GLint const Helper, GLint const Shadows, GLint const Normals, GLint const Diffuse ) {

View File

@@ -55,9 +55,10 @@ private:
void load_TGA();
void set_filtering() const;
void downsize( GLuint const Format );
void flip_vertical();
// members
std::vector<char> data; // texture data
std::vector<char> data; // texture data (stored GL-style, bottom-left origin)
resource_state data_state{ resource_state::none }; // current state of texture data
int data_width{ 0 },
data_height{ 0 },

View File

@@ -46,42 +46,6 @@ control_mapper::find( TSubModel const *Control ) const {
}
}
TCab::TCab()
{
CabPos1.x = -1.0;
CabPos1.y = 1.0;
CabPos1.z = 1.0;
CabPos2.x = 1.0;
CabPos2.y = 1.0;
CabPos2.z = -1.0;
bEnabled = false;
bOccupied = true;
dimm_r = dimm_g = dimm_b = 1;
intlit_r = intlit_g = intlit_b = 0;
intlitlow_r = intlitlow_g = intlitlow_b = 0;
/*
iGaugesMax = 100; // 95 - trzeba pobierać to z pliku konfiguracyjnego
ggList = new TGauge[iGaugesMax];
iGauges = 0; // na razie nie są dodane
iButtonsMax = 60; // 55 - trzeba pobierać to z pliku konfiguracyjnego
btList = new TButton[iButtonsMax];
iButtons = 0;
*/
}
/*
void TCab::Init(double Initx1, double Inity1, double Initz1, double Initx2, double Inity2,
double Initz2, bool InitEnabled, bool InitOccupied)
{
CabPos1.x = Initx1;
CabPos1.y = Inity1;
CabPos1.z = Initz1;
CabPos2.x = Initx2;
CabPos2.y = Inity2;
CabPos2.z = Initz2;
bEnabled = InitEnabled;
bOccupied = InitOccupied;
}
*/
void TCab::Load(cParser &Parser)
{
// NOTE: clearing control tables here is bit of a crutch, imposed by current scheme of loading compartments anew on each cab change
@@ -95,15 +59,15 @@ void TCab::Load(cParser &Parser)
{
Parser.getTokens( 9, false );
Parser
>> dimm_r
>> dimm_g
>> dimm_b
>> intlit_r
>> intlit_g
>> intlit_b
>> intlitlow_r
>> intlitlow_g
>> intlitlow_b;
>> dimm.r
>> dimm.g
>> dimm.b
>> intlit.r
>> intlit.g
>> intlit.b
>> intlitlow.r
>> intlitlow.g
>> intlitlow.b;
Parser.getTokens(); Parser >> token;
}
CabPos1.x = std::stod( token );
@@ -119,14 +83,6 @@ void TCab::Load(cParser &Parser)
bOccupied = true;
}
TCab::~TCab()
{
/*
delete[] ggList;
delete[] btList;
*/
};
TGauge &TCab::Gauge(int n)
{ // pobranie adresu obiektu aniomowanego ruchem
/*
@@ -427,12 +383,13 @@ bool TTrain::Init(TDynamicObject *NewDynamicObject, bool e3d)
}
PyObject *TTrain::GetTrainState() {
PyObject *dict = PyDict_New();
if( dict == NULL ) {
return NULL;
}
auto const &mover = DynamicObject->MoverParameters;
auto *dict = PyDict_New();
if( ( dict == nullptr )
|| ( mover == nullptr ) ) {
return nullptr;
}
PyDict_SetItemString( dict, "cab", PyGetInt( mover->ActiveCab ) );
// basic systems state data
@@ -3110,7 +3067,8 @@ void TTrain::OnCommand_radiochanneldecrease( TTrain *Train, command_data const &
void TTrain::OnCommand_radiostopsend( TTrain *Train, command_data const &Command ) {
if( Command.action == GLFW_PRESS ) {
if( true == Train->mvOccupied->Radio ) {
if( ( true == Train->mvOccupied->Radio )
&& ( Train->mvControlled->Battery || Train->mvControlled->ConverterFlag ) ) {
simulation::Region->RadioStop( Train->Dynamic()->GetPosition() );
}
// visual feedback
@@ -3125,7 +3083,8 @@ void TTrain::OnCommand_radiostopsend( TTrain *Train, command_data const &Command
void TTrain::OnCommand_radiostoptest( TTrain *Train, command_data const &Command ) {
if( Command.action == GLFW_PRESS ) {
if( Train->RadioChannel() == 10 ) {
if( ( Train->RadioChannel() == 10 )
&& ( Train->mvControlled->Battery || Train->mvControlled->ConverterFlag ) ) {
Train->Dynamic()->RadioStop();
}
// visual feedback

50
Train.h
View File

@@ -28,35 +28,27 @@ const float fConverterPrzekaznik = 1.5f; // hunter-261211: do przekaznika nadmia
// const double fBuzzerTime= 5.0f;
const float fHaslerTime = 1.2f;
class TCab
{
public:
TCab();
~TCab();
/*
void Init(double Initx1, double Inity1, double Initz1, double Initx2, double Inity2, double Initz2, bool InitEnabled, bool InitOccupied);
*/
class TCab {
public:
// methods
void Load(cParser &Parser);
Math3D::vector3 CabPos1;
Math3D::vector3 CabPos2;
bool bEnabled;
bool bOccupied;
double dimm_r, dimm_g, dimm_b; // McZapkie-120503: tlumienie swiatla
double intlit_r, intlit_g, intlit_b; // McZapkie-120503: oswietlenie kabiny
double intlitlow_r, intlitlow_g, intlitlow_b; // McZapkie-120503: przyciemnione oswietlenie kabiny
private:
/*
TGauge *ggList; // Ra 2014-08: lista animacji macierzowych (gałek) w kabinie
int iGaugesMax, iGauges; // ile miejsca w tablicy i ile jest w użyciu
TButton *btList; // Ra 2014-08: lista animacji dwustanowych (lampek) w kabinie
int iButtonsMax, iButtons; // ile miejsca w tablicy i ile jest w użyciu
*/
std::vector<TGauge> ggList;
std::vector<TButton> btList;
public:
TGauge &Gauge(int n = -1); // pobranie adresu obiektu
TButton &Button(int n = -1); // pobranie adresu obiektu
void Update();
// members
Math3D::vector3 CabPos1 { 0, 1, 1 };
Math3D::vector3 CabPos2 { 0, 1, -1 };
bool bEnabled { false };
bool bOccupied { true };
glm::vec3 dimm; // McZapkie-120503: tlumienie swiatla
glm::vec3 intlit; // McZapkie-120503: oswietlenie kabiny
glm::vec3 intlitlow; // McZapkie-120503: przyciemnione oswietlenie kabiny
TGauge &Gauge( int n = -1 ); // pobranie adresu obiektu
TButton &Button( int n = -1 ); // pobranie adresu obiektu
private:
// members
std::vector<TGauge> ggList;
std::vector<TButton> btList;
};
class control_mapper {
@@ -449,13 +441,13 @@ public: // reszta może by?publiczna
sound_source rsHissE { sound_placement::internal, EU07_SOUND_CABCONTROLSCUTOFFRANGE }; // nagle
sound_source rsHissX { sound_placement::internal, EU07_SOUND_CABCONTROLSCUTOFFRANGE }; // fala
sound_source rsHissT { sound_placement::internal, EU07_SOUND_CABCONTROLSCUTOFFRANGE }; // czasowy
sound_source rsSBHiss { sound_placement::internal, EU07_SOUND_CABCONTROLSCUTOFFRANGE }; // local
sound_source rsSBHiss { sound_placement::internal, EU07_SOUND_CABCONTROLSCUTOFFRANGE }; // local
sound_source rsSBHissU { sound_placement::internal, EU07_SOUND_CABCONTROLSCUTOFFRANGE }; // local, engage brakes
float m_lastlocalbrakepressure { -1.f }; // helper, cached level of pressure in local brake cylinder
float m_localbrakepressurechange { 0.f }; // recent change of pressure in local brake cylinder
sound_source rsFadeSound { sound_placement::internal, EU07_SOUND_CABCONTROLSCUTOFFRANGE };
sound_source rsRunningNoise{ sound_placement::internal, 2 * EU07_SOUND_CABCONTROLSCUTOFFRANGE };
sound_source rsRunningNoise{ sound_placement::internal, EU07_SOUND_GLOBALRANGE };
sound_source dsbHasler { sound_placement::internal, EU07_SOUND_CABCONTROLSCUTOFFRANGE };
sound_source dsbBuzzer { sound_placement::internal, EU07_SOUND_CABCONTROLSCUTOFFRANGE };

View File

@@ -30,16 +30,21 @@ openal_buffer::openal_buffer( std::string const &Filename ) :
if( Filename.substr( Filename.rfind( '.' ) ) == ".wav" ) {
// .wav file
auto *file { drwav_open_file( Filename.c_str() ) };
rate = file->sampleRate;
auto const samplecount { static_cast<std::size_t>( file->totalSampleCount ) };
data.resize( samplecount );
drwav_read_s16(
file,
samplecount,
&data[ 0 ] );
if( file->channels > 1 ) {
narrow_to_mono( file->channels );
data.resize( samplecount / file->channels );
if( file != nullptr ) {
rate = file->sampleRate;
auto const samplecount{ static_cast<std::size_t>( file->totalSampleCount ) };
data.resize( samplecount );
drwav_read_s16(
file,
samplecount,
&data[ 0 ] );
if( file->channels > 1 ) {
narrow_to_mono( file->channels );
data.resize( samplecount / file->channels );
}
}
else {
ErrorLog( "Bad file: failed do load audio file \"" + Filename + "\"", logtype::file );
}
// we're done with the disk data
drwav_close( file );
@@ -47,26 +52,32 @@ openal_buffer::openal_buffer( std::string const &Filename ) :
else {
// .flac or .ogg file
auto *file { drflac_open_file( Filename.c_str() ) };
rate = file->sampleRate;
auto const samplecount{ static_cast<std::size_t>( file->totalSampleCount ) };
data.resize( samplecount );
drflac_read_s16(
file,
samplecount,
&data[ 0 ] );
if( file->channels > 1 ) {
narrow_to_mono( file->channels );
data.resize( samplecount / file->channels );
if( file != nullptr ) {
rate = file->sampleRate;
auto const samplecount{ static_cast<std::size_t>( file->totalSampleCount ) };
data.resize( samplecount );
drflac_read_s16(
file,
samplecount,
&data[ 0 ] );
if( file->channels > 1 ) {
narrow_to_mono( file->channels );
data.resize( samplecount / file->channels );
}
}
else {
ErrorLog( "Bad file: failed do load audio file \"" + Filename + "\"", logtype::file );
}
// we're done with the disk data
drflac_close( file );
}
// send the data to openal side
::alBufferData( id, AL_FORMAT_MONO16, data.data(), data.size() * sizeof( std::int16_t ), rate );
// and get rid of the source, we shouldn't need it anymore
// TBD, TODO: delay data fetching and transfers until the buffer is actually used?
std::vector<std::int16_t>().swap( data );
if( false == data.empty() ) {
// send the data to openal side
::alBufferData( id, AL_FORMAT_MONO16, data.data(), data.size() * sizeof( std::int16_t ), rate );
// and get rid of the source, we shouldn't need it anymore
// TBD, TODO: delay data fetching and transfers until the buffer is actually used?
std::vector<std::int16_t>().swap( data );
}
fetch_caption();
}
@@ -166,7 +177,7 @@ buffer_manager::create( std::string const &Filename ) {
return emplace( filelookup );
}
// if we still didn't find anything, give up
ErrorLog( "Bad file: failed do locate audio file \"" + Filename + "\"" );
ErrorLog( "Bad file: failed do locate audio file \"" + Filename + "\"", logtype::file );
return null_handle;
}

View File

@@ -13,6 +13,7 @@ http://mozilla.org/MPL/2.0/.
#include "classes.h"
#include "names.h"
float const EU07_SOUND_GLOBALRANGE { -1.f };
float const EU07_SOUND_CABCONTROLSCUTOFFRANGE { 7.5f };
float const EU07_SOUND_BRAKINGCUTOFFRANGE { 100.f };
float const EU07_SOUND_RUNNINGNOISECUTOFFRANGE { 200.f };

View File

@@ -1,5 +1,5 @@
#pragma once
#define VERSION_MAJOR 18
#define VERSION_MINOR 131
#define VERSION_MINOR 202
#define VERSION_REVISION 0