Browse Source

egg2pg: Add egg-force-srgb-textures environment variable

This will cause all textures in .egg files to be loaded with an sRGB format setting (except with an envtype that generally assumes a linear texture).

Fixes #1006
rdb 5 years ago
parent
commit
c7f75fc906

+ 7 - 0
panda/src/egg2pg/config_egg2pg.cxx

@@ -194,6 +194,13 @@ ConfigVariableBool egg_implicit_alpha_binary
           "will automatically be downgraded to alpha type \"binary\" instead of "
           "will automatically be downgraded to alpha type \"binary\" instead of "
           "whatever appears in the egg file."));
           "whatever appears in the egg file."));
 
 
+ConfigVariableBool egg_force_srgb_textures
+("egg-force-srgb-textures", false,
+ PRC_DESC("If this is true, Panda3D will automatically assign the F_srgb or "
+          "F_srgb_alpha format to all textures loaded from egg files, unless "
+          "their envtype is set to a non-color map.  Keep in mind that the "
+          "model-cache must be cleared after changing this setting."));
+
 ConfigureFn(config_egg2pg) {
 ConfigureFn(config_egg2pg) {
   init_libegg2pg();
   init_libegg2pg();
 }
 }

+ 1 - 0
panda/src/egg2pg/config_egg2pg.h

@@ -54,6 +54,7 @@ extern EXPCL_PANDA_EGG2PG ConfigVariableBool egg_preload_simple_textures;
 extern EXPCL_PANDA_EGG2PG ConfigVariableDouble egg_vertex_membership_quantize;
 extern EXPCL_PANDA_EGG2PG ConfigVariableDouble egg_vertex_membership_quantize;
 extern EXPCL_PANDA_EGG2PG ConfigVariableInt egg_vertex_max_num_joints;
 extern EXPCL_PANDA_EGG2PG ConfigVariableInt egg_vertex_max_num_joints;
 extern EXPCL_PANDA_EGG2PG ConfigVariableBool egg_implicit_alpha_binary;
 extern EXPCL_PANDA_EGG2PG ConfigVariableBool egg_implicit_alpha_binary;
+extern EXPCL_PANDA_EGG2PG ConfigVariableBool egg_force_srgb_textures;
 
 
 extern EXPCL_PANDA_EGG2PG void init_libegg2pg();
 extern EXPCL_PANDA_EGG2PG void init_libegg2pg();
 
 

+ 74 - 27
panda/src/egg2pg/eggLoader.cxx

@@ -1188,6 +1188,30 @@ apply_texture_attributes(Texture *tex, const EggTexture *egg_tex) {
 
 
   tex->set_default_sampler(sampler);
   tex->set_default_sampler(sampler);
 
 
+  bool force_srgb = false;
+  if (egg_force_srgb_textures) {
+    switch (egg_tex->get_env_type()) {
+    case EggTexture::ET_unspecified:
+    case EggTexture::ET_modulate:
+    case EggTexture::ET_decal:
+    case EggTexture::ET_blend:
+    case EggTexture::ET_replace:
+    case EggTexture::ET_add:
+    case EggTexture::ET_blend_color_scale:
+    case EggTexture::ET_modulate_glow:
+    case EggTexture::ET_modulate_gloss:
+      force_srgb = true;
+      if (egg2pg_cat.is_debug()) {
+        egg2pg_cat.debug()
+          << "Enabling sRGB format on texture " << egg_tex->get_name() << "\n";
+      }
+      break;
+
+    default:
+      break;
+    }
+  }
+
   if (tex->get_num_components() == 1) {
   if (tex->get_num_components() == 1) {
     switch (egg_tex->get_format()) {
     switch (egg_tex->get_format()) {
     case EggTexture::F_red:
     case EggTexture::F_red:
@@ -1203,44 +1227,52 @@ apply_texture_attributes(Texture *tex, const EggTexture *egg_tex) {
       tex->set_format(Texture::F_alpha);
       tex->set_format(Texture::F_alpha);
       break;
       break;
     case EggTexture::F_luminance:
     case EggTexture::F_luminance:
-      tex->set_format(Texture::F_luminance);
-      break;
-
-    case EggTexture::F_unspecified:
+      tex->set_format(force_srgb ? Texture::F_sluminance : Texture::F_luminance);
       break;
       break;
 
 
     default:
     default:
       egg2pg_cat.warning()
       egg2pg_cat.warning()
         << "Ignoring inappropriate format " << egg_tex->get_format()
         << "Ignoring inappropriate format " << egg_tex->get_format()
         << " for 1-component texture " << egg_tex->get_name() << "\n";
         << " for 1-component texture " << egg_tex->get_name() << "\n";
+
+    case EggTexture::F_unspecified:
+      if (force_srgb) {
+        tex->set_format(Texture::F_sluminance);
+      }
+      break;
     }
     }
 
 
   } else if (tex->get_num_components() == 2) {
   } else if (tex->get_num_components() == 2) {
     switch (egg_tex->get_format()) {
     switch (egg_tex->get_format()) {
     case EggTexture::F_luminance_alpha:
     case EggTexture::F_luminance_alpha:
-      tex->set_format(Texture::F_luminance_alpha);
+      tex->set_format(force_srgb ? Texture::F_sluminance_alpha : Texture::F_luminance_alpha);
       break;
       break;
 
 
     case EggTexture::F_luminance_alphamask:
     case EggTexture::F_luminance_alphamask:
-      tex->set_format(Texture::F_luminance_alphamask);
-      break;
-
-    case EggTexture::F_unspecified:
+      tex->set_format(force_srgb ? Texture::F_sluminance_alpha : Texture::F_luminance_alphamask);
       break;
       break;
 
 
     default:
     default:
       egg2pg_cat.warning()
       egg2pg_cat.warning()
         << "Ignoring inappropriate format " << egg_tex->get_format()
         << "Ignoring inappropriate format " << egg_tex->get_format()
         << " for 2-component texture " << egg_tex->get_name() << "\n";
         << " for 2-component texture " << egg_tex->get_name() << "\n";
+
+    case EggTexture::F_unspecified:
+      if (force_srgb) {
+        tex->set_format(Texture::F_sluminance_alpha);
+      }
+      break;
     }
     }
 
 
   } else if (tex->get_num_components() == 3) {
   } else if (tex->get_num_components() == 3) {
     switch (egg_tex->get_format()) {
     switch (egg_tex->get_format()) {
     case EggTexture::F_rgb:
     case EggTexture::F_rgb:
-      tex->set_format(Texture::F_rgb);
+      tex->set_format(force_srgb ? Texture::F_srgb : Texture::F_rgb);
       break;
       break;
     case EggTexture::F_rgb12:
     case EggTexture::F_rgb12:
-      if (tex->get_component_width() >= 2) {
+      if (force_srgb) {
+        tex->set_format(Texture::F_srgb);
+      } else if (tex->get_component_width() >= 2) {
         // Only do this if the component width supports it.
         // Only do this if the component width supports it.
         tex->set_format(Texture::F_rgb12);
         tex->set_format(Texture::F_rgb12);
       } else {
       } else {
@@ -1253,40 +1285,45 @@ apply_texture_attributes(Texture *tex, const EggTexture *egg_tex) {
     case EggTexture::F_rgba8:
     case EggTexture::F_rgba8:
       // We'll quietly accept RGBA8 for a 3-component texture, since flt2egg
       // We'll quietly accept RGBA8 for a 3-component texture, since flt2egg
       // generates these for 3-component as well as for 4-component textures.
       // generates these for 3-component as well as for 4-component textures.
-      tex->set_format(Texture::F_rgb8);
+      tex->set_format(force_srgb ? Texture::F_srgb : Texture::F_rgb8);
       break;
       break;
     case EggTexture::F_rgb5:
     case EggTexture::F_rgb5:
-      tex->set_format(Texture::F_rgb5);
+      tex->set_format(force_srgb ? Texture::F_srgb : Texture::F_rgb5);
       break;
       break;
     case EggTexture::F_rgb332:
     case EggTexture::F_rgb332:
-      tex->set_format(Texture::F_rgb332);
+      tex->set_format(force_srgb ? Texture::F_srgb : Texture::F_rgb332);
       break;
       break;
     case EggTexture::F_srgb:
     case EggTexture::F_srgb:
     case EggTexture::F_srgb_alpha:
     case EggTexture::F_srgb_alpha:
       tex->set_format(Texture::F_srgb);
       tex->set_format(Texture::F_srgb);
       break;
       break;
 
 
-    case EggTexture::F_unspecified:
-      break;
-
     default:
     default:
       egg2pg_cat.warning()
       egg2pg_cat.warning()
         << "Ignoring inappropriate format " << egg_tex->get_format()
         << "Ignoring inappropriate format " << egg_tex->get_format()
         << " for 3-component texture " << egg_tex->get_name() << "\n";
         << " for 3-component texture " << egg_tex->get_name() << "\n";
+
+    case EggTexture::F_unspecified:
+      if (force_srgb) {
+        tex->set_format(Texture::F_srgb);
+      }
+      break;
     }
     }
 
 
   } else if (tex->get_num_components() == 4) {
   } else if (tex->get_num_components() == 4) {
     switch (egg_tex->get_format()) {
     switch (egg_tex->get_format()) {
     case EggTexture::F_rgba:
     case EggTexture::F_rgba:
-      tex->set_format(Texture::F_rgba);
+      tex->set_format(force_srgb ? Texture::F_srgb_alpha : Texture::F_rgba);
       break;
       break;
     case EggTexture::F_rgbm:
     case EggTexture::F_rgbm:
-      tex->set_format(Texture::F_rgbm);
+      tex->set_format(force_srgb ? Texture::F_srgb_alpha : Texture::F_rgbm);
       break;
       break;
     case EggTexture::F_rgba12:
     case EggTexture::F_rgba12:
-      if (tex->get_component_width() >= 2) {
+      if (force_srgb) {
+        tex->set_format(Texture::F_srgb_alpha);
+      } else if (tex->get_component_width() >= 2) {
         // Only do this if the component width supports it.
         // Only do this if the component width supports it.
-        tex->set_format(Texture::F_rgba12);
+        tex->set_format(force_srgb ? Texture::F_srgb_alpha : Texture::F_rgba12);
       } else {
       } else {
         egg2pg_cat.warning()
         egg2pg_cat.warning()
           << "Ignoring inappropriate format " << egg_tex->get_format()
           << "Ignoring inappropriate format " << egg_tex->get_format()
@@ -1294,28 +1331,38 @@ apply_texture_attributes(Texture *tex, const EggTexture *egg_tex) {
       }
       }
       break;
       break;
     case EggTexture::F_rgba8:
     case EggTexture::F_rgba8:
-      tex->set_format(Texture::F_rgba8);
+      tex->set_format(force_srgb ? Texture::F_srgb_alpha : Texture::F_rgba8);
       break;
       break;
     case EggTexture::F_rgba4:
     case EggTexture::F_rgba4:
-      tex->set_format(Texture::F_rgba4);
+      tex->set_format(force_srgb ? Texture::F_srgb_alpha : Texture::F_rgba4);
       break;
       break;
     case EggTexture::F_rgba5:
     case EggTexture::F_rgba5:
-      tex->set_format(Texture::F_rgba5);
+      tex->set_format(force_srgb ? Texture::F_srgb_alpha : Texture::F_rgba5);
       break;
       break;
     case EggTexture::F_srgb_alpha:
     case EggTexture::F_srgb_alpha:
       tex->set_format(Texture::F_srgb_alpha);
       tex->set_format(Texture::F_srgb_alpha);
       break;
       break;
 
 
-    case EggTexture::F_unspecified:
-      break;
-
     default:
     default:
       egg2pg_cat.warning()
       egg2pg_cat.warning()
         << "Ignoring inappropriate format " << egg_tex->get_format()
         << "Ignoring inappropriate format " << egg_tex->get_format()
         << " for 4-component texture " << egg_tex->get_name() << "\n";
         << " for 4-component texture " << egg_tex->get_name() << "\n";
+
+    case EggTexture::F_unspecified:
+      if (force_srgb) {
+        tex->set_format(Texture::F_srgb_alpha);
+      }
+      break;
     }
     }
   }
   }
 
 
+  if (force_srgb && tex->get_format() != Texture::F_alpha &&
+      !Texture::is_srgb(tex->get_format())) {
+    egg2pg_cat.warning()
+      << "Unable to enable sRGB format on texture " << egg_tex->get_name()
+      << " with specified format " << egg_tex->get_format() << "\n";
+  }
+
   switch (egg_tex->get_quality_level()) {
   switch (egg_tex->get_quality_level()) {
   case EggTexture::QL_unspecified:
   case EggTexture::QL_unspecified:
   case EggTexture::QL_default:
   case EggTexture::QL_default: