mirror of
https://github.com/MaSzyna-EU07/maszyna.git
synced 2026-07-21 17:09:19 +02:00
opacity bugfix
This commit is contained in:
@@ -434,7 +434,7 @@ bool TAnimModel::Init(std::string const &asName, std::string const &asReplacable
|
||||
m_materialdata.replacable_skins[ 1 ] = GfxRenderer.Fetch_Material( asReplacableTexture );
|
||||
}
|
||||
if( ( m_materialdata.replacable_skins[ 1 ] != null_handle )
|
||||
&& ( GfxRenderer.Material( m_materialdata.replacable_skins[ 1 ] ).opacity == 0.0f ) ) {
|
||||
&& ( GfxRenderer.Material( m_materialdata.replacable_skins[ 1 ] ).get_or_guess_opacity() == 0.0f ) ) {
|
||||
// tekstura z kanałem alfa - nie renderować w cyklu nieprzezroczystych
|
||||
m_materialdata.textures_alpha = 0x31310031;
|
||||
}
|
||||
|
||||
12
DynObj.cpp
12
DynObj.cpp
@@ -4587,27 +4587,31 @@ void TDynamicObject::LoadMMediaFile( std::string BaseDir, std::string TypeName,
|
||||
else {
|
||||
m_materialdata.replacable_skins[ 1 ] = GfxRenderer.Fetch_Material( ReplacableSkin );
|
||||
}
|
||||
if( GfxRenderer.Material( m_materialdata.replacable_skins[ 1 ] ).opacity == 0.0f ) {
|
||||
|
||||
if( GfxRenderer.Material( m_materialdata.replacable_skins[ 1 ] ).get_or_guess_opacity() == 0.0f ) {
|
||||
// tekstura -1 z kanałem alfa - nie renderować w cyklu nieprzezroczystych
|
||||
WriteLog("alpha");
|
||||
m_materialdata.textures_alpha = 0x31310031;
|
||||
}
|
||||
else {
|
||||
// wszystkie tekstury nieprzezroczyste - nie renderować w cyklu przezroczystych
|
||||
WriteLog("opaque");
|
||||
m_materialdata.textures_alpha = 0x30300030;
|
||||
}
|
||||
|
||||
if( ( m_materialdata.replacable_skins[ 2 ] )
|
||||
&& ( GfxRenderer.Material( m_materialdata.replacable_skins[ 2 ] ).opacity == 0.0f ) ) {
|
||||
&& ( GfxRenderer.Material( m_materialdata.replacable_skins[ 2 ] ).get_or_guess_opacity() == 0.0f ) ) {
|
||||
WriteLog("alpha");
|
||||
// tekstura -2 z kanałem alfa - nie renderować w cyklu nieprzezroczystych
|
||||
m_materialdata.textures_alpha |= 0x02020002;
|
||||
}
|
||||
if( ( m_materialdata.replacable_skins[ 3 ] )
|
||||
&& ( GfxRenderer.Material( m_materialdata.replacable_skins[ 3 ] ).opacity == 0.0f ) ) {
|
||||
&& ( GfxRenderer.Material( m_materialdata.replacable_skins[ 3 ] ).get_or_guess_opacity() == 0.0f ) ) {
|
||||
// tekstura -3 z kanałem alfa - nie renderować w cyklu nieprzezroczystych
|
||||
m_materialdata.textures_alpha |= 0x04040004;
|
||||
}
|
||||
if( ( m_materialdata.replacable_skins[ 4 ] )
|
||||
&& ( GfxRenderer.Material( m_materialdata.replacable_skins[ 4 ] ).opacity == 0.0f ) ) {
|
||||
&& ( GfxRenderer.Material( m_materialdata.replacable_skins[ 4 ] ).get_or_guess_opacity() == 0.0f ) ) {
|
||||
// tekstura -4 z kanałem alfa - nie renderować w cyklu nieprzezroczystych
|
||||
m_materialdata.textures_alpha |= 0x08080008;
|
||||
}
|
||||
|
||||
62
Model3d.cpp
62
Model3d.cpp
@@ -309,27 +309,27 @@ int TSubModel::Load( cParser &parser, TModel3d *Model, /*int Pos,*/ bool dynamic
|
||||
else if (material.find("replacableskin") != material.npos)
|
||||
{ // McZapkie-060702: zmienialne skory modelu
|
||||
m_material = -1;
|
||||
iFlags |= (Opacity == 1.0f) ? 1 : 0x10; // zmienna tekstura 1
|
||||
iFlags |= (Opacity < 1.0) ? 1 : 0x10; // zmienna tekstura 1
|
||||
}
|
||||
else if (material == "-1")
|
||||
{
|
||||
m_material = -1;
|
||||
iFlags |= (Opacity == 1.0f) ? 1 : 0x10; // zmienna tekstura 1
|
||||
iFlags |= (Opacity < 1.0) ? 1 : 0x10; // zmienna tekstura 1
|
||||
}
|
||||
else if (material == "-2")
|
||||
{
|
||||
m_material = -2;
|
||||
iFlags |= (Opacity == 1.0f) ? 2 : 0x10; // zmienna tekstura 2
|
||||
iFlags |= (Opacity < 1.0) ? 2 : 0x10; // zmienna tekstura 2
|
||||
}
|
||||
else if (material == "-3")
|
||||
{
|
||||
m_material = -3;
|
||||
iFlags |= (Opacity == 1.0f) ? 4 : 0x10; // zmienna tekstura 3
|
||||
iFlags |= (Opacity < 1.0) ? 4 : 0x10; // zmienna tekstura 3
|
||||
}
|
||||
else if (material == "-4")
|
||||
{
|
||||
m_material = -4;
|
||||
iFlags |= (Opacity == 1.0f) ? 8 : 0x10; // zmienna tekstura 4
|
||||
iFlags |= (Opacity < 1.0) ? 8 : 0x10; // zmienna tekstura 4
|
||||
}
|
||||
else {
|
||||
Name_Material(material);
|
||||
@@ -341,14 +341,8 @@ int TSubModel::Load( cParser &parser, TModel3d *Model, /*int Pos,*/ bool dynamic
|
||||
*/
|
||||
m_material = GfxRenderer.Fetch_Material( material );
|
||||
// renderowanie w cyklu przezroczystych tylko jeśli:
|
||||
// 1. Opacity=0 (przejściowo <1, czy tam <100) oraz
|
||||
// 2. tekstura ma przezroczystość
|
||||
iFlags |=
|
||||
( ( ( Opacity == 0.0f )
|
||||
&& ( ( m_material != null_handle )
|
||||
&& ( GfxRenderer.Material( m_material ).opacity == 0.0f ) ) ) ?
|
||||
0x20 :
|
||||
0x10 ); // 0x10-nieprzezroczysta, 0x20-przezroczysta
|
||||
// 1. Opacity=0 (przejściowo <1, czy tam <100)
|
||||
iFlags |= Opacity < 1.0f ? 0x20 : 0x10 ; // 0x20-przezroczysta, 0x10-nieprzezroczysta
|
||||
};
|
||||
}
|
||||
else if (eType == TP_STARS)
|
||||
@@ -359,6 +353,27 @@ int TSubModel::Load( cParser &parser, TModel3d *Model, /*int Pos,*/ bool dynamic
|
||||
else
|
||||
iFlags |= 0x10;
|
||||
|
||||
if (m_material != null_handle)
|
||||
{
|
||||
opengl_material &mat = GfxRenderer.Material(m_material);
|
||||
// if material don't have opacity set, set legacy submodel opacity
|
||||
if (std::isnan(mat.opacity))
|
||||
{
|
||||
if (iFlags & 0x20) // translucent
|
||||
mat.opacity = 0.0f;
|
||||
else if (iFlags & 0x10) // opaque
|
||||
mat.opacity = 0.5f;
|
||||
}
|
||||
else // but if it does, replace submodel opacity with material one
|
||||
{
|
||||
iFlags &= ~0x30;
|
||||
if (mat.opacity == 0.0f)
|
||||
iFlags |= 0x20; // translucent
|
||||
else
|
||||
iFlags |= 0x10; // opaque
|
||||
}
|
||||
}
|
||||
|
||||
// visibility range
|
||||
std::string discard;
|
||||
parser.getTokens(5, false);
|
||||
@@ -1683,13 +1698,20 @@ void TSubModel::BinInit(TSubModel *s, float4x4 *m, std::vector<std::string> *t,
|
||||
}
|
||||
*/
|
||||
m_material = GfxRenderer.Fetch_Material( m_materialname );
|
||||
if( ( iFlags & 0x30 ) == 0 ) {
|
||||
// texture-alpha based fallback if for some reason we don't have opacity flag set yet
|
||||
iFlags |= (
|
||||
( ( m_material != null_handle )
|
||||
&& ( GfxRenderer.Material( m_material ).opacity == 0.0f ) ) ?
|
||||
0x20 :
|
||||
0x10 ); // 0x10-nieprzezroczysta, 0x20-przezroczysta
|
||||
|
||||
// if we don't have phase flags set for some reason, try to fix it
|
||||
if (!(iFlags & 0x30) && m_material != null_handle)
|
||||
{
|
||||
opengl_material &mat = GfxRenderer.Material(m_material);
|
||||
if (std::isnan(mat.opacity))
|
||||
// if material don't have opacity set, try to guess it
|
||||
mat.opacity = mat.get_or_guess_opacity();
|
||||
|
||||
// set phase flag based on material opacity
|
||||
if (mat.opacity == 0.0f)
|
||||
iFlags |= 0x20; // translucent
|
||||
else
|
||||
iFlags |= 0x10; // opaque
|
||||
}
|
||||
}
|
||||
else {
|
||||
|
||||
20
Track.cpp
20
Track.cpp
@@ -563,15 +563,21 @@ void TTrack::Load(cParser *parser, Math3D::vector3 pOrigin)
|
||||
else if (iCategoryFlag & 2)
|
||||
if (m_material1 && fTexLength)
|
||||
{ // dla drogi trzeba ustalić proporcje boków nawierzchni
|
||||
float w, h;
|
||||
GfxRenderer.Bind_Material(m_material1);
|
||||
glGetTexLevelParameterfv(GL_TEXTURE_2D, 0, GL_TEXTURE_WIDTH, &w);
|
||||
glGetTexLevelParameterfv(GL_TEXTURE_2D, 0, GL_TEXTURE_HEIGHT, &h);
|
||||
float w = 1.0f, h = 1.0f;
|
||||
opengl_material &mat1 = GfxRenderer.Material(m_material1);
|
||||
if (mat1.textures[0] != null_handle)
|
||||
{
|
||||
w = GfxRenderer.Texture(mat1.textures[0]).width();
|
||||
h = GfxRenderer.Texture(mat1.textures[0]).height();
|
||||
}
|
||||
if (h != 0.0)
|
||||
fTexRatio1 = w / h; // proporcja boków
|
||||
GfxRenderer.Bind_Material(m_material2);
|
||||
glGetTexLevelParameterfv(GL_TEXTURE_2D, 0, GL_TEXTURE_WIDTH, &w);
|
||||
glGetTexLevelParameterfv(GL_TEXTURE_2D, 0, GL_TEXTURE_HEIGHT, &h);
|
||||
opengl_material &mat2 = GfxRenderer.Material(m_material2);
|
||||
if (mat2.textures[0] != null_handle)
|
||||
{
|
||||
w = GfxRenderer.Texture(mat2.textures[0]).width();
|
||||
h = GfxRenderer.Texture(mat2.textures[0]).height();
|
||||
}
|
||||
if (h != 0.0)
|
||||
fTexRatio2 = w / h; // proporcja boków
|
||||
}
|
||||
|
||||
24
material.cpp
24
material.cpp
@@ -117,6 +117,23 @@ opengl_material::deserialize_mapping( cParser &Input, int const Priority, bool c
|
||||
return true; // return value marks a key: value pair was extracted, nothing about whether it's recognized
|
||||
}
|
||||
|
||||
float opengl_material::get_or_guess_opacity()
|
||||
{
|
||||
if (!std::isnan(opacity))
|
||||
return opacity;
|
||||
|
||||
if (textures[0] != null_handle)
|
||||
{
|
||||
opengl_texture &tex = GfxRenderer.Texture(textures[0]);
|
||||
if (tex.has_alpha)
|
||||
return 0.0f;
|
||||
else
|
||||
return 0.5f;
|
||||
}
|
||||
|
||||
return 0.0f;
|
||||
}
|
||||
|
||||
std::unordered_map<gl::shader::components_e, GLint> material_manager::components_mapping =
|
||||
{
|
||||
{ gl::shader::components_e::R, GL_RED },
|
||||
@@ -183,13 +200,6 @@ material_manager::create( std::string const &Filename, bool const Loadnow ) {
|
||||
GfxRenderer.Texture(handle).set_components_hint(components_mapping[entry.components]);
|
||||
}
|
||||
|
||||
if (std::isnan(material.opacity))
|
||||
{
|
||||
material.opacity = 1.0f;
|
||||
if (material.textures[0] != null_handle)
|
||||
material.opacity = GfxRenderer.Texture( material.textures[0] ).has_alpha ? 0.0f : 1.0f;
|
||||
}
|
||||
|
||||
material_handle handle = m_materials.size();
|
||||
m_materials.emplace_back( material );
|
||||
m_materialmappings.emplace( material.name, handle );
|
||||
|
||||
@@ -36,6 +36,7 @@ struct opengl_material {
|
||||
// methods
|
||||
bool
|
||||
deserialize( cParser &Input, bool const Loadnow );
|
||||
float get_or_guess_opacity();
|
||||
|
||||
private:
|
||||
// methods
|
||||
|
||||
21
renderer.cpp
21
renderer.cpp
@@ -825,15 +825,15 @@ void opengl_renderer::setup_matrices()
|
||||
|
||||
void opengl_renderer::setup_drawing(bool const Alpha)
|
||||
{
|
||||
if (true == Alpha)
|
||||
if (Alpha)
|
||||
{
|
||||
::glEnable(GL_BLEND);
|
||||
m_blendphase = true;
|
||||
m_blendingenabled = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
::glDisable(GL_BLEND);
|
||||
m_blendphase = false;
|
||||
m_blendingenabled = false;
|
||||
}
|
||||
|
||||
switch (m_renderpass.draw_mode)
|
||||
@@ -853,6 +853,7 @@ void opengl_renderer::setup_drawing(bool const Alpha)
|
||||
case rendermode::pickcontrols:
|
||||
case rendermode::pickscenery:
|
||||
{
|
||||
glCullFace(GL_BACK);
|
||||
break;
|
||||
}
|
||||
default:
|
||||
@@ -1077,10 +1078,11 @@ void opengl_renderer::Bind_Material(material_handle const Material)
|
||||
for (size_t i = 0; i < gl::MAX_PARAMS; i++)
|
||||
model_ubs.param[i] = material.params[i];
|
||||
|
||||
if (m_blendphase)
|
||||
model_ubs.opacity = 0.0f;
|
||||
// if for some reason material don't have opacity set, guess it based on render phase
|
||||
if (std::isnan(material.opacity))
|
||||
model_ubs.opacity = m_blendingenabled ? 0.0f : 0.5f;
|
||||
else
|
||||
model_ubs.opacity = 1.0f;
|
||||
model_ubs.opacity = material.opacity;
|
||||
|
||||
material.shader->bind();
|
||||
|
||||
@@ -1120,6 +1122,12 @@ opengl_material const &opengl_renderer::Material(material_handle const Material)
|
||||
return m_materials.material(Material);
|
||||
}
|
||||
|
||||
opengl_material &opengl_renderer::Material(material_handle const Material)
|
||||
{
|
||||
return m_materials.material(Material);
|
||||
}
|
||||
|
||||
|
||||
texture_handle opengl_renderer::Fetch_Texture(std::string const &Filename, bool const Loadnow, GLint format_hint)
|
||||
{
|
||||
return m_textures.create(Filename, Loadnow, format_hint);
|
||||
@@ -1127,7 +1135,6 @@ texture_handle opengl_renderer::Fetch_Texture(std::string const &Filename, bool
|
||||
|
||||
void opengl_renderer::Bind_Texture(size_t Unit, texture_handle const Texture)
|
||||
{
|
||||
|
||||
m_textures.bind(Unit, Texture);
|
||||
}
|
||||
|
||||
|
||||
@@ -157,6 +157,7 @@ class opengl_renderer
|
||||
std::shared_ptr<gl::program> Fetch_Shader(std::string const &name);
|
||||
|
||||
opengl_material const &Material(material_handle const Material) const;
|
||||
opengl_material &Material(material_handle const Material);
|
||||
// texture methods
|
||||
texture_handle Fetch_Texture(std::string const &Filename, bool const Loadnow = true, GLint format_hint = GL_SRGB_ALPHA);
|
||||
void Bind_Texture(size_t Unit, texture_handle const Texture);
|
||||
@@ -381,7 +382,7 @@ class opengl_renderer
|
||||
|
||||
material_handle m_invalid_material;
|
||||
|
||||
bool m_blendphase; // m7t: todo: remove kludge!
|
||||
bool m_blendingenabled;
|
||||
|
||||
bool m_widelines_supported;
|
||||
};
|
||||
|
||||
@@ -340,7 +340,7 @@ shape_node::convert( TSubModel const *Submodel ) {
|
||||
m_data.lighting.diffuse = Submodel->f4Diffuse;
|
||||
m_data.lighting.specular = Submodel->f4Specular;
|
||||
m_data.material = Submodel->m_material;
|
||||
m_data.translucent = ( GfxRenderer.Material( m_data.material ).opacity == 0.0f );
|
||||
m_data.translucent = ( GfxRenderer.Material( m_data.material ).get_or_guess_opacity() == 0.0f );
|
||||
// NOTE: we set unlimited view range typical for terrain, because we don't expect to convert any other 3d models
|
||||
m_data.rangesquared_max = std::numeric_limits<double>::max();
|
||||
|
||||
|
||||
@@ -92,16 +92,8 @@ void main()
|
||||
{
|
||||
vec4 tex_color = texture(tex1, f_coord);
|
||||
|
||||
if (opacity == 0.0f)
|
||||
{
|
||||
//blending
|
||||
}
|
||||
else
|
||||
{
|
||||
//test
|
||||
if (tex_color.a < 0.5f)
|
||||
discard;
|
||||
}
|
||||
if (tex_color.a < opacity)
|
||||
discard;
|
||||
|
||||
vec3 envcolor = texture(envmap, reflect(f_pos, normalize(f_normal))).rgb;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user