fix wrl files with pixel image textures not importing correctly #4

Merged
Cedric Steiert merged 2 commits from Bujus_Krachus/io_scene_x3d:fix-wrl-import-image-texture into main 2024-08-06 17:23:53 +02:00

View File

@ -8,6 +8,7 @@ DEBUG = False
import os import os
import shlex import shlex
import math import math
import re
from math import sin, cos, pi from math import sin, cos, pi
from itertools import chain from itertools import chain
@ -2993,17 +2994,34 @@ def importShape_LoadAppearance(vrmlname, appr, ancestry, node, is_vcol):
def appearance_LoadPixelTexture(pixelTexture, ancestry): def appearance_LoadPixelTexture(pixelTexture, ancestry):
def extract_pixel_colors(data_string):
"""
Read all hexadecimal pixel color values, distributed across multiple fields (mutliline)
"""
# Use a regular expression to find all hexadecimal color values
hex_pattern = re.compile(r'0x[0-9a-fA-F]{6}')
pixel_colors = hex_pattern.findall(data_string)
# Convert hexadecimal color values to integers
pixel_colors = [int(color, 0) for color in pixel_colors]
return pixel_colors
image = pixelTexture.getFieldAsArray('image', 0, ancestry) image = pixelTexture.getFieldAsArray('image', 0, ancestry)
# read width, height and plane_count value, assuming all are in one field called 'image' (singleline)
(w, h, plane_count) = image[0:3] (w, h, plane_count) = image[0:3]
has_alpha = plane_count in {2, 4} has_alpha = plane_count in {2, 4}
# get either hex color values (multiline) or regular color values (singleline)
pixels = extract_pixel_colors(str(pixelTexture)) # converting to string may not be ideal, but works
if len(pixels) == 0:
pixels = image[3:] pixels = image[3:]
if len(pixels) != w * h: if len(pixels) != w * h:
print("ImportX3D warning: pixel count in PixelTexture is off") print(f"ImportX3D warning: pixel count in PixelTexture is off. Pixels: {len(pixels)}, Width: {w}, Height: {h}")
bpyima = bpy.data.images.new("PixelTexture", w, h, has_alpha, True) bpyima = bpy.data.images.new("PixelTexture", w, h, alpha=has_alpha, float_buffer=True)
if not has_alpha: if not has_alpha:
bpyima.alpha_mode = 'NONE' bpyima.alpha_mode = 'NONE'
# as some image textures may have no pixel data, ignore those
if len(pixels) != 0:
# Conditional above the loop, for performance # Conditional above the loop, for performance
if plane_count == 3: # RGB if plane_count == 3: # RGB
bpyima.pixels = [(cco & 0xff) / 255 for pixel in pixels bpyima.pixels = [(cco & 0xff) / 255 for pixel in pixels