# Error handling
Simplygon API reports errors through the error handling class ErrorHandler. A user can derive a class from ErrorHandler, which then will receive processing errors, and handle them appropriately. In C# and Python, if no error handler is set, the errors are reported through exception handling.
This example shows how to use the Simplygon error handler.
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.
#include <string>
#include <stdlib.h>
#include <filesystem>
#include <future>
#include "SimplygonLoader.h"
class CustomErrorHandler : public Simplygon::ErrorHandler
{
public:
void HandleError(Simplygon::spObject object, const char* interfaceName, const char* methodName, Simplygon::rid errorType , const char* errorText) override
{
printf("Error (%s:%s): %s\n", interfaceName, methodName, errorText);
}
} customErrorHandler;
void CheckLog(Simplygon::ISimplygon* sg)
{
// Check if any errors occurred.
bool hasErrors = sg->ErrorOccurred();
if (hasErrors)
{
Simplygon::spStringArray errors = sg->CreateStringArray();
sg->GetErrorMessages(errors);
auto errorCount = errors->GetItemCount();
if (errorCount > 0)
{
printf("%s\n", "Errors:");
for (auto errorIndex = 0U; errorIndex < errorCount; ++errorIndex)
{
Simplygon::spString errorString = errors->GetItem((int)errorIndex);
printf("%s\n", errorString.c_str());
}
sg->ClearErrorMessages();
}
}
else
{
printf("%s\n", "No errors.");
}
// Check if any warnings occurred.
bool hasWarnings = sg->WarningOccurred();
if (hasWarnings)
{
Simplygon::spStringArray warnings = sg->CreateStringArray();
sg->GetWarningMessages(warnings);
auto warningCount = warnings->GetItemCount();
if (warningCount > 0)
{
printf("%s\n", "Warnings:");
for (auto warningIndex = 0U; warningIndex < warningCount; ++warningIndex)
{
Simplygon::spString warningString = warnings->GetItem((int)warningIndex);
printf("%s\n", warningString.c_str());
}
sg->ClearWarningMessages();
}
}
else
{
printf("%s\n", "No warnings.");
}
}
void RunReduction(Simplygon::ISimplygon* sg)
{
// Set the custom error handler to the Simplygon interface.
sg->SetErrorHandler(&customErrorHandler);
// Create the reduction pipeline.
Simplygon::spReductionPipeline sgReductionPipeline = sg->CreateReductionPipeline();
// To be able to use the T-Junction remover, the welder has to be enabled so this will trigger an
// error.
Simplygon::spRepairSettings sgRepairSettings = sgReductionPipeline->GetRepairSettings();
sgRepairSettings->SetUseWelding( false );
sgRepairSettings->SetUseTJunctionRemover( true );
// Start the reduction pipeline and the faulty settings will cause an error.
printf("%s\n", "Start the reduction pipeline and the faulty settings will cause an error.");
sgReductionPipeline->RunSceneFromFile("../../../Assets/SimplygonMan/SimplygonMan.obj", "output.fbx", Simplygon::EPipelineRunMode::RunInNewProcess);
// Check log for any warnings or errors.
printf("%s\n", "Check log for any warnings or errors.");
CheckLog(sg);
}
int main()
{
Simplygon::ISimplygon* sg = NULL;
Simplygon::EErrorCodes initval = Simplygon::Initialize( &sg );
if( initval != Simplygon::EErrorCodes::NoError )
{
printf( "Failed to initialize Simplygon: ErrorCode(%d)", (int)initval );
return int(initval);
}
RunReduction(sg);
Simplygon::Deinitialize(sg);
return 0;
}
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.
using System;
using System.IO;
using System.Threading.Tasks;
public class CustomErrorHandler : Simplygon.ErrorHandler
{
public override void HandleError(Simplygon.spObject obj, string interfaceName, string methodName, int errorType , string errorText)
{
Console.WriteLine($"Error ({interfaceName}:{methodName}): {errorText}");
}
}
public class Program
{
static private CustomErrorHandler customErrorHandler;
static void CheckLog(Simplygon.ISimplygon sg)
{
// Check if any errors occurred.
bool hasErrors = sg.ErrorOccurred();
if (hasErrors)
{
Simplygon.spStringArray errors = sg.CreateStringArray();
sg.GetErrorMessages(errors);
var errorCount = errors.GetItemCount();
if (errorCount > 0)
{
Console.WriteLine("Errors:");
for (uint errorIndex = 0; errorIndex < errorCount; ++errorIndex)
{
string errorString = errors.GetItem((int)errorIndex);
Console.WriteLine(errorString);
}
sg.ClearErrorMessages();
}
}
else
{
Console.WriteLine("No errors.");
}
// Check if any warnings occurred.
bool hasWarnings = sg.WarningOccurred();
if (hasWarnings)
{
Simplygon.spStringArray warnings = sg.CreateStringArray();
sg.GetWarningMessages(warnings);
var warningCount = warnings.GetItemCount();
if (warningCount > 0)
{
Console.WriteLine("Warnings:");
for (uint warningIndex = 0; warningIndex < warningCount; ++warningIndex)
{
string warningString = warnings.GetItem((int)warningIndex);
Console.WriteLine(warningString);
}
sg.ClearWarningMessages();
}
}
else
{
Console.WriteLine("No warnings.");
}
}
static void RunReduction(Simplygon.ISimplygon sg)
{
// Set the custom error handler to the Simplygon interface.
sg.SetErrorHandler(customErrorHandler);
// Create the reduction pipeline.
using Simplygon.spReductionPipeline sgReductionPipeline = sg.CreateReductionPipeline();
// To be able to use the T-Junction remover, the welder has to be enabled so this will trigger an
// error.
using Simplygon.spRepairSettings sgRepairSettings = sgReductionPipeline.GetRepairSettings();
sgRepairSettings.SetUseWelding( false );
sgRepairSettings.SetUseTJunctionRemover( true );
// Start the reduction pipeline and the faulty settings will cause an error.
Console.WriteLine("Start the reduction pipeline and the faulty settings will cause an error.");
sgReductionPipeline.RunSceneFromFile("../../../Assets/SimplygonMan/SimplygonMan.obj", "output.fbx", Simplygon.EPipelineRunMode.RunInNewProcess);
// Check log for any warnings or errors.
Console.WriteLine("Check log for any warnings or errors.");
CheckLog(sg);
}
static int Main(string[] args)
{
using var sg = Simplygon.Loader.InitSimplygon(out var errorCode, out var errorMessage);
if (errorCode != Simplygon.EErrorCodes.NoError)
{
Console.WriteLine( $"Failed to initialize Simplygon: ErrorCode({(int)errorCode}) {errorMessage}" );
return (int)errorCode;
}
customErrorHandler = new CustomErrorHandler();
RunReduction(sg);
return 0;
}
}
# Copyright (c) Microsoft Corporation.
# Licensed under the MIT License.
import math
import os
import sys
import glob
import gc
import threading
from pathlib import Path
from simplygon import simplygon_loader
from simplygon import Simplygon
class CustomErrorHandler(Simplygon.ErrorHandler):
def HandleError(self, object: Simplygon.spObject, interfaceName: str, methodName: str, errorType: int, errorText: str):
print('Error (%s:%s): %s' %(interfaceName, methodName, errorText))
customErrorHandler = CustomErrorHandler()
def CheckLog(sg: Simplygon.ISimplygon):
# Check if any errors occurred.
hasErrors = sg.ErrorOccurred()
if hasErrors:
errors = sg.CreateStringArray()
sg.GetErrorMessages(errors)
errorCount = errors.GetItemCount()
if errorCount > 0:
print("Errors:")
for errorIndex in range(errorCount):
errorString = errors.GetItem(errorIndex)
print(errorString)
sg.ClearErrorMessages()
else:
print("No errors.")
# Check if any warnings occurred.
hasWarnings = sg.WarningOccurred()
if hasWarnings:
warnings = sg.CreateStringArray()
sg.GetWarningMessages(warnings)
warningCount = warnings.GetItemCount()
if warningCount > 0:
print("Warnings:")
for warningIndex in range(warningCount):
warningString = warnings.GetItem(warningIndex)
print(warningString)
sg.ClearWarningMessages()
else:
print("No warnings.")
def RunReduction(sg: Simplygon.ISimplygon):
# Set the custom error handler to the Simplygon interface.
sg.SetErrorHandler(customErrorHandler)
# Create the reduction pipeline.
sgReductionPipeline = sg.CreateReductionPipeline()
# To be able to use the T-Junction remover, the welder has to be enabled so this will trigger an
# error.
sgRepairSettings = sgReductionPipeline.GetRepairSettings()
sgRepairSettings.SetUseWelding( False )
sgRepairSettings.SetUseTJunctionRemover( True )
# Start the reduction pipeline and the faulty settings will cause an error.
print("Start the reduction pipeline and the faulty settings will cause an error.")
sgReductionPipeline.RunSceneFromFile("../../../Assets/SimplygonMan/SimplygonMan.obj", "output.fbx", Simplygon.EPipelineRunMode_RunInNewProcess)
# Check log for any warnings or errors.
print("Check log for any warnings or errors.")
CheckLog(sg)
if __name__ == '__main__':
sg = simplygon_loader.init_simplygon()
if sg is None:
exit(Simplygon.GetLastInitializationError())
RunReduction(sg)
sg = None
gc.collect()