Improved PSK vertex color importing to be per-corner instead of per-vertex
Previously, the importer was storing the vertex colors in the point domain. However, the PSK itself stores colors per "wedge", which maps to corners, resulting in the "ambiguous vertex colors" warning if two corners mapped to the same vertex but had different colors. The new method is now more correct and doesn't discard data.
This commit is contained in:
@@ -1,4 +1,3 @@
|
|||||||
from math import inf
|
|
||||||
from typing import Optional, List
|
from typing import Optional, List
|
||||||
|
|
||||||
import bmesh
|
import bmesh
|
||||||
@@ -17,7 +16,7 @@ class PskImportOptions:
|
|||||||
self.should_import_mesh = True
|
self.should_import_mesh = True
|
||||||
self.should_reuse_materials = True
|
self.should_reuse_materials = True
|
||||||
self.should_import_vertex_colors = True
|
self.should_import_vertex_colors = True
|
||||||
self.vertex_color_space = 'sRGB'
|
self.vertex_color_space = 'SRGB'
|
||||||
self.should_import_vertex_normals = True
|
self.should_import_vertex_normals = True
|
||||||
self.should_import_extra_uvs = True
|
self.should_import_extra_uvs = True
|
||||||
self.should_import_skeleton = True
|
self.should_import_skeleton = True
|
||||||
@@ -144,6 +143,7 @@ def import_psk(psk: Psk, context, options: PskImportOptions) -> PskImportResult:
|
|||||||
|
|
||||||
bm.verts.ensure_lookup_table()
|
bm.verts.ensure_lookup_table()
|
||||||
|
|
||||||
|
# FACES
|
||||||
invalid_face_indices = set()
|
invalid_face_indices = set()
|
||||||
for face_index, face in enumerate(psk.faces):
|
for face_index, face in enumerate(psk.faces):
|
||||||
point_indices = map(lambda i: psk.wedges[i].point_index, reversed(face.wedge_indices))
|
point_indices = map(lambda i: psk.wedges[i].point_index, reversed(face.wedge_indices))
|
||||||
@@ -192,33 +192,28 @@ def import_psk(psk: Psk, context, options: PskImportOptions) -> PskImportResult:
|
|||||||
|
|
||||||
# VERTEX COLORS
|
# VERTEX COLORS
|
||||||
if psk.has_vertex_colors and options.should_import_vertex_colors:
|
if psk.has_vertex_colors and options.should_import_vertex_colors:
|
||||||
size = (len(psk.points), 4)
|
# Convert vertex colors to sRGB if necessary.
|
||||||
vertex_colors = np.full(size, inf)
|
psk_vertex_colors = np.zeros((len(psk.vertex_colors), 4))
|
||||||
vertex_color_data = mesh_data.vertex_colors.new(name='VERTEXCOLOR')
|
for i in range(len(psk.vertex_colors)):
|
||||||
ambiguous_vertex_color_point_indices = []
|
psk_vertex_colors[i,:] = psk.vertex_colors[i].normalized()
|
||||||
|
match options.vertex_color_space:
|
||||||
|
case 'SRGBA':
|
||||||
|
for i in range(psk_vertex_colors.shape[0]):
|
||||||
|
psk_vertex_colors[i, :3] = tuple(map(lambda x: rgb_to_srgb(x), psk_vertex_colors[i, :3]))
|
||||||
|
case _:
|
||||||
|
pass
|
||||||
|
|
||||||
for wedge_index, wedge in enumerate(psk.wedges):
|
# Map the PSK vertex colors to the face corners.
|
||||||
point_index = wedge.point_index
|
face_corner_colors = np.full((len(psk.faces * 3), 4), 1.0)
|
||||||
psk_vertex_color = psk.vertex_colors[wedge_index].normalized()
|
face_corner_color_index = 0
|
||||||
if vertex_colors[point_index, 0] != inf and tuple(vertex_colors[point_index]) != psk_vertex_color:
|
for face_index, face in enumerate(psk.faces):
|
||||||
ambiguous_vertex_color_point_indices.append(point_index)
|
for wedge_index in reversed(face.wedge_indices):
|
||||||
else:
|
face_corner_colors[face_corner_color_index] = psk_vertex_colors[wedge_index]
|
||||||
vertex_colors[point_index] = psk_vertex_color
|
face_corner_color_index += 1
|
||||||
|
|
||||||
if options.vertex_color_space == 'SRGBA':
|
# Create the vertex color attribute.
|
||||||
for i in range(vertex_colors.shape[0]):
|
face_corner_color_attribute = mesh_data.attributes.new(name='VERTEXCOLOR', type='FLOAT_COLOR', domain='CORNER')
|
||||||
vertex_colors[i, :3] = tuple(map(lambda x: rgb_to_srgb(x), vertex_colors[i, :3]))
|
face_corner_color_attribute.data.foreach_set('color', face_corner_colors.flatten())
|
||||||
|
|
||||||
for loop_index, loop in enumerate(mesh_data.loops):
|
|
||||||
vertex_color = vertex_colors[loop.vertex_index]
|
|
||||||
if vertex_color is not None:
|
|
||||||
vertex_color_data.data[loop_index].color = vertex_color
|
|
||||||
else:
|
|
||||||
vertex_color_data.data[loop_index].color = 1.0, 1.0, 1.0, 1.0
|
|
||||||
|
|
||||||
if len(ambiguous_vertex_color_point_indices) > 0:
|
|
||||||
result.warnings.append(
|
|
||||||
f'{len(ambiguous_vertex_color_point_indices)} vertex(es) with ambiguous vertex colors.')
|
|
||||||
|
|
||||||
# VERTEX NORMALS
|
# VERTEX NORMALS
|
||||||
if psk.has_vertex_normals and options.should_import_vertex_normals:
|
if psk.has_vertex_normals and options.should_import_vertex_normals:
|
||||||
|
|||||||
Reference in New Issue
Block a user