diff --git a/korman/exporter/etlight.py b/korman/exporter/etlight.py index 119242b..fec2c2f 100644 --- a/korman/exporter/etlight.py +++ b/korman/exporter/etlight.py @@ -51,9 +51,12 @@ class LightBaker(_MeshManager): def _apply_render_settings(self, toggle, vcols): render = bpy.context.scene.render - toggle.track(render, "use_textures", False) + + # Remember, lightmaps carefully control the enabled textures such that light + # can be cast through transparent materials. See diatribe in lightmap prep. + toggle.track(render, "use_textures", not vcols) toggle.track(render, "use_shadows", True) - toggle.track(render, "use_envmaps", False) + toggle.track(render, "use_envmaps", True) toggle.track(render, "use_raytrace", True) toggle.track(render, "bake_type", "FULL") toggle.track(render, "use_bake_clear", True) @@ -243,6 +246,18 @@ class LightBaker(_MeshManager): modifier = bo.plasma_modifiers.lightmap uv_textures = mesh.uv_textures + # Previously, we told Blender to just ignore textures althogether when baking + # VCols or lightmaps. This is easy, but it prevents us from doing tricks like + # using the "Receive Transparent" option, which allows for light to be cast + # through sections of materials that are transparent. Therefore, on objects + # that are lightmapped, we will disable all the texture slots... + # Due to our batching, however, materials that are transparent cannot be lightmapped. + for material in (i for i in mesh.materials if i is not None): + if material.use_transparency: + raise ExportError("'{}': Cannot lightmap material '{}' because it is transparnt".format(bo.name, material.name)) + for slot in (j for j in material.texture_slots if j is not None): + toggle.track(slot, "use", False) + # Create a special light group for baking if not self._generate_lightgroup(bo, modifier.lights): return False @@ -357,7 +372,7 @@ class LightBaker(_MeshManager): for i in bpy.data.objects: if i == objs: # prevents proper baking to texture - for mat in i.data.materials: + for mat in (j for j in i.data.materials if j is not None): toggle.track(mat, "use_vertex_color_paint", False) i.select = True else: @@ -370,7 +385,7 @@ class LightBaker(_MeshManager): value = i in objs if value: # prevents proper baking to texture - for mat in i.data.materials: + for mat in (j for j in i.data.materials if j is not None): toggle.track(mat, "use_vertex_color_paint", False) toggle.track(i, "hide_render", False) elif isinstance(i.data, bpy.types.Mesh) and not self._has_valid_material(i): diff --git a/korman/render.py b/korman/render.py index d478ef4..393b9eb 100644 --- a/korman/render.py +++ b/korman/render.py @@ -33,6 +33,7 @@ properties_material.MATERIAL_PT_specular.COMPAT_ENGINES.add("PLASMA_GAME") properties_material.MATERIAL_PT_options.COMPAT_ENGINES.add("PLASMA_GAME") properties_material.MATERIAL_PT_preview.COMPAT_ENGINES.add("PLASMA_GAME") properties_material.MATERIAL_PT_transp.COMPAT_ENGINES.add("PLASMA_GAME") +properties_material.MATERIAL_PT_shadow.COMPAT_ENGINES.add("PLASMA_GAME") del properties_material from bl_ui import properties_data_mesh diff --git a/korman/ui/modifiers/render.py b/korman/ui/modifiers/render.py index 34063c2..be79b78 100644 --- a/korman/ui/modifiers/render.py +++ b/korman/ui/modifiers/render.py @@ -87,17 +87,21 @@ def lightmap(modifier, layout, context): layout.prop(modifier, "lights") layout.prop_search(modifier, "uv_map", context.active_object.data, "uv_textures") - operator = layout.operator("object.plasma_lightmap_preview", "Preview Lightmap", icon="RENDER_STILL") - - # Kind of clever stuff to show the user a preview... - # We can't show images, so we make a hidden ImageTexture called LIGHTMAPGEN_PREVIEW. We check - # the backing image name to see if it's for this lightmap. If so, you have a preview. If not, - # well... It was nice knowing you! - tex = bpy.data.textures.get("LIGHTMAPGEN_PREVIEW") - if tex is not None and tex.image is not None: - im_name = "{}_LIGHTMAPGEN.png".format(context.active_object.name) - if tex.image.name == im_name: - layout.template_preview(tex, show_buttons=False) + # Lightmaps can only be applied to objects with opaque materials. + if any((i.use_transparency for i in modifier.id_data.data.materials if i is not None)): + layout.label("Transparent objects cannot be lightmapped.", icon="ERROR") + else: + operator = layout.operator("object.plasma_lightmap_preview", "Preview Lightmap", icon="RENDER_STILL") + + # Kind of clever stuff to show the user a preview... + # We can't show images, so we make a hidden ImageTexture called LIGHTMAPGEN_PREVIEW. We check + # the backing image name to see if it's for this lightmap. If so, you have a preview. If not, + # well... It was nice knowing you! + tex = bpy.data.textures.get("LIGHTMAPGEN_PREVIEW") + if tex is not None and tex.image is not None: + im_name = "{}_LIGHTMAPGEN.png".format(context.active_object.name) + if tex.image.name == im_name: + layout.template_preview(tex, show_buttons=False) def rtshadow(modifier, layout, context): split = layout.split()