CtrlK
BlogDocsLog inGet started
Tessl Logo

tessl/pypi-pywavefront

Python library for importing Wavefront .obj files and generating interleaved vertex data ready for rendering.

Pending

Quality

Pending

Does it follow best practices?

Impact

Pending

No eval scenarios have been run

Overview
Eval results
Files

configuration.mddocs/

Configuration and Utilities

Logging configuration, exception handling, and utility functions for customizing PyWavefront behavior and debugging.

Capabilities

Logging Configuration

PyWavefront provides configurable logging for debugging and monitoring parsing operations.

def configure_logging(level, formatter=None) -> None:
    """
    Configure PyWavefront's logging system.
    
    Parameters:
    - level: Logging level (logging.DEBUG, logging.INFO, logging.WARNING, logging.ERROR)
    - formatter: Optional logging.Formatter instance for custom formatting
    
    Default behavior:
    - Logger name: "pywavefront"
    - Default level: ERROR
    - Default handler: StreamHandler (console output)
    """

Default Logging Configuration:

  • Logger name: "pywavefront"
  • Default level: ERROR (only errors shown)
  • Output: Console via StreamHandler

Exception Handling

class PywavefrontException(Exception):
    """
    Custom exception class for PyWavefront-specific errors.
    
    Raised for:
    - File parsing errors
    - Missing material references
    - Unsupported .obj features in strict mode
    - File access issues
    - Malformed geometry data
    """

Common Exception Scenarios:

  • File not found or permission denied
  • Invalid .obj syntax or malformed data
  • Missing .mtl files when create_materials=False
  • Unknown material references in usemtl statements
  • Unsupported features when strict=True
  • Encoding issues with international characters

Version Information

__version__: str  # Current version string
import pywavefront
print(pywavefront.__version__)  # "1.3.3"

Usage Examples

Basic Logging Setup

import logging
import pywavefront

# Enable debug logging for detailed parsing information
pywavefront.configure_logging(logging.DEBUG)

# Load a file with debug output
scene = pywavefront.Wavefront('model.obj')
# Output: Debug information about parsing progress, timing, etc.

Custom Logging Formatter

import logging
import pywavefront

# Create a custom formatter
formatter = logging.Formatter(
    '%(asctime)s - %(name)s - %(levelname)s - %(message)s'
)

# Configure with custom formatter
pywavefront.configure_logging(logging.INFO, formatter=formatter)

# Load with timestamped logging
scene = pywavefront.Wavefront('model.obj')

Logging Levels and Output

import logging
import pywavefront

# Different logging levels show different information:

# ERROR (default): Only critical errors
pywavefront.configure_logging(logging.ERROR)

# WARNING: Warnings about potential issues
pywavefront.configure_logging(logging.WARNING)

# INFO: General information about parsing progress
pywavefront.configure_logging(logging.INFO)

# DEBUG: Detailed parsing information and timing
pywavefront.configure_logging(logging.DEBUG)

Exception Handling

import pywavefront

try:
    # Strict parsing that raises exceptions for unsupported features
    scene = pywavefront.Wavefront('model.obj', strict=True)
    
except pywavefront.PywavefrontException as e:
    print(f"PyWavefront error: {e}")
    # Handle PyWavefront-specific errors
    
except FileNotFoundError as e:
    print(f"File not found: {e}")
    # Handle file access errors
    
except Exception as e:
    print(f"Unexpected error: {e}")
    # Handle other unexpected errors

# Graceful handling of missing materials
try:
    scene = pywavefront.Wavefront('model_with_missing_mtl.obj')
except pywavefront.PywavefrontException:
    print("Missing materials detected, creating defaults...")
    scene = pywavefront.Wavefront('model_with_missing_mtl.obj', create_materials=True)

Debugging File Loading Issues

import logging
import pywavefront

# Enable debug logging to troubleshoot loading issues
pywavefront.configure_logging(logging.DEBUG)

try:
    # Load with maximum debugging information
    scene = pywavefront.Wavefront(
        'problematic_model.obj',
        strict=True,      # Catch parsing issues
        encoding='utf-8'  # Ensure correct encoding
    )
    
    print(f"Successfully loaded {len(scene.materials)} materials")
    print(f"Found {len(scene.mesh_list)} meshes")
    
except pywavefront.PywavefrontException as e:
    print(f"Parsing failed: {e}")
    
    # Try with relaxed settings
    print("Retrying with relaxed parsing...")
    scene = pywavefront.Wavefront(
        'problematic_model.obj',
        strict=False,
        create_materials=True
    )

Performance Monitoring

import time
import logging
import pywavefront

# Configure INFO level to see load timing
pywavefront.configure_logging(logging.INFO)

start_time = time.time()

# Load with caching for performance
scene = pywavefront.Wavefront('large_model.obj', cache=True)

load_time = time.time() - start_time
print(f"Load completed in {load_time:.2f} seconds")

# Subsequent loads will be much faster due to caching
start_time = time.time()
scene2 = pywavefront.Wavefront('large_model.obj', cache=True)
cached_load_time = time.time() - start_time
print(f"Cached load completed in {cached_load_time:.2f} seconds")
print(f"Speedup: {load_time / cached_load_time:.1f}x")

Error Recovery Strategies

import pywavefront

def load_model_robust(filepath):
    """Robust model loading with multiple fallback strategies."""
    
    # Strategy 1: Normal loading
    try:
        return pywavefront.Wavefront(filepath)
    except pywavefront.PywavefrontException:
        pass
    
    # Strategy 2: Create missing materials
    try:
        return pywavefront.Wavefront(filepath, create_materials=True)
    except pywavefront.PywavefrontException:
        pass
    
    # Strategy 3: Disable strict parsing
    try:
        return pywavefront.Wavefront(
            filepath, 
            strict=False, 
            create_materials=True
        )
    except pywavefront.PywavefrontException:
        pass
    
    # Strategy 4: Try different encoding
    try:
        return pywavefront.Wavefront(
            filepath,
            encoding='latin1',
            strict=False,
            create_materials=True
        )
    except Exception as e:
        raise pywavefront.PywavefrontException(
            f"Failed to load {filepath} with all strategies: {e}"
        )

# Usage
try:
    scene = load_model_robust('difficult_model.obj')
    print("Model loaded successfully")
except pywavefront.PywavefrontException as e:
    print(f"All loading strategies failed: {e}")

Logging Output Examples

DEBUG Level Output:

pywavefront: Load time: 0.123
pywavefront: Parsing vertex data: 1000 vertices
pywavefront: Loading material library: materials.mtl
pywavefront: Created material: wood_material
pywavefront: Face parsing complete: 500 triangular faces

INFO Level Output:

pywavefront: model.obj: Load time: 0.123

WARNING Level Output:

pywavefront: Unknown material reference: missing_material
pywavefront: Creating default material: default0

ERROR Level Output:

pywavefront: Failed to load material library: materials.mtl
pywavefront: PywavefrontException: Unknown material: metal_surface

Install with Tessl CLI

npx tessl i tessl/pypi-pywavefront

docs

configuration.md

file-loading.md

index.md

materials.md

mesh-operations.md

visualization.md

tile.json