Skip to content

Latest commit

 

History

History
1312 lines (990 loc) · 46.8 KB

File metadata and controls

1312 lines (990 loc) · 46.8 KB

PicoGK API Reference

Comprehensive reference for the public C# API of PicoGK 1.7.x. Everything lives in the PicoGK namespace. The reference is organized by topic; a file map at the end maps API areas to source files in this repo.

Conventions used in PicoGK:

  • nFoo for int returns/params, fFoo for float, bFoo for bool, vecFoo for Vector3/Vector2, clrFoo for color, oFoo for object/struct, vox/msh/lat for Voxels/Mesh/Lattice instances, str for string
  • Methods on instances ending in (no leading verb prefix) usually mutate; methods like voxXxx/mshXxx/oXxx typically return a new copy
  • Coordinates are real-world millimetres unless otherwise stated; the global voxel size is set once via Library.Go(fVoxelSizeMM, …)

Table of contents

  1. Library lifecycle
  2. Voxels
  3. Mesh
  4. Lattice
  5. ScalarField
  6. VectorField
  7. Implicit interfaces
  8. FieldMetadata
  9. OpenVdbFile
  10. STL I/O
  11. Slicing: PolyContour, PolySlice, PolySliceStack
  12. CLI file I/O
  13. PolyLine
  14. Image and TGA
  15. Viewer
  16. Animations and Easing
  17. Field utilities (SDF visualization, traversal helpers)
  18. Geometric primitives: Utils
  19. Filesystem and string helpers: Utils, TempFolder
  20. Logging: LogFile
  21. CSV: CsvTable
  22. Vector3 extensions
  23. Math types: Coord, Triangle, BBox2, BBox3
  24. Color types
  25. Config
  26. Source file map

Library lifecycle

Source: PicoGK_Library.cs

The Library static class initializes the native runtime, owns the singleton viewer/log, and exposes voxel-size constants. Two ways to use it:

Library.Go: interactive mode (with viewer + log)

public static void Go(  float        _fVoxelSizeMM,
                        ThreadStart  fnTask,
                        string       strLogFolder    = "",
                        string       strLogFileName  = "",
                        string       strSrcFolder    = "",
                        string       strLightsFile   = "",
                        bool         bEndAppWithTask = false);

Initializes the runtime with the given voxel size, creates the log file and viewer, then runs fnTask on a worker thread while the viewer runs on the main thread. Throws if called more than once per process.

Library: headless mode (no viewer)

public Library(float _fVoxelSizeMM);          // ctor — opens runtime
public void   Dispose();                       // closes runtime

Use with using (var lib = new Library(0.1f)) { … }. No viewer or log file is created.

Task control

public static bool bContinueTask(bool bAppExitOnly = false); // call periodically; false => exit
public static void EndTask();                                // ask task to stop
public static void CancelEndTaskRequest();                   // cancel a prior EndTask

Viewer + log accessors

public static Viewer  oViewer();                              // singleton viewer (after Go)
public static void    Log(in string strFormat, params object[] args);

Runtime info

public static string strName();        // native runtime name
public static string strVersion();     // native runtime version (e.g. "1.7.7")
public static string strBuildInfo();   // build date / metadata

Coordinate conversion

public static Vector3 vecVoxelsToMm(int x, int y, int z);
public static void    MmToVoxels(Vector3 vecMm, out int x, out int y, out int z);

Constants and globals

public static float  fVoxelSizeMM;       // set by Go() / Library ctor
public static string strLogFolder;
public static string strSrcFolder;
public const  int    nStringLength = 255; // max string length passed to native

Light setup helper

public static string strFindLightSetupFile(string strInputFolder, out string strSearched);

Voxels

Source: PicoGK_Voxels.cs, I/O in PicoGK_VoxelsIo.cs, CLI export in PicoGK_Cli.cs

Voxels wraps an OpenVDB narrow-band signed-distance level set. It is the workhorse type. Boolean ops, offsets, mesh/implicit/lattice rendering, slicing, ray casting all live here.

Construction

public Voxels();                                   // empty field
public Voxels(in Voxels voxSource);                // copy
public Voxels(in Mesh msh);                        // voxelize a (closed) mesh
public Voxels(in Lattice lat);                     // voxelize a lattice
public Voxels(in IImplicit xImplicit, in BBox3 oBounds); // render implicit SDF
public Voxels(in IBoundedImplicit xImplicit);      // bounded implicit
public Voxels(in ScalarField oSource);             // build from existing SDF scalar field

public Voxels voxDuplicate();                       // deep copy
public Mesh   mshAsMesh();                          // marching-cubes mesh
public static Voxels voxSphere(Vector3 vecCenter, float fRadius);

Boolean operations (mutating + functional)

// Union
public void   BoolAdd(in Voxels voxOperand);
public Voxels voxBoolAdd(in Voxels voxOperand);
public void   BoolAddAll(in IEnumerable<Voxels> avoxList);
public Voxels voxBoolAddAll(in IEnumerable<Voxels> avoxList);
public static Voxels voxCombine(in Voxels vox1, in Voxels vox2);
public static Voxels voxCombineAll(in IEnumerable<Voxels> avoxList);

// Difference
public void   BoolSubtract(in Voxels voxOperand);
public Voxels voxBoolSubtract(in Voxels voxOperand);
public void   BoolSubtractAll(in IEnumerable<Voxels> avoxList);
public Voxels voxBoolSubtractAll(in IEnumerable<Voxels> avoxList);

// Intersection
public void   BoolIntersect(in Voxels voxOperand);
public Voxels voxBoolIntersect(in Voxels voxOperand);

// Operators
public static Voxels operator +(Voxels a, Voxels b); // BoolAdd
public static Voxels operator -(Voxels a, Voxels b); // BoolSubtract
public static Voxels operator &(Voxels a, Voxels b); // BoolIntersect

// Trim to bounding box
public void Trim(BBox3 oBox);

Offsetting and smoothing

public void   Offset(float fDistMM);                  // outward (+) / inward (-)
public Voxels voxOffset(float fDistMM);
public void   DoubleOffset(float fDist1MM, float fDist2MM);
public Voxels voxDoubleOffset(float fDist1MM, float fDist2MM);
public void   TripleOffset(float fDistMM);            // smoothen by removing detail < fDistMM
public Voxels voxTripleOffset(float fDistMM);
public void   Smoothen(float fDistMM);                // alias for TripleOffset
public Voxels voxSmoothen(float fDistMM);

public void   OverOffset(float fFirstOffsetMM, float fFinalSurfaceDistInMM = 0);
public Voxels voxOverOffset(float fFirstOffsetMM, float fFinalSurfaceDistInMM = 0);

public void   Fillet(float fRoundingMM);              // OverOffset wrapper, fillet-like
public Voxels voxFillet(float fRoundingMM);

public Voxels voxShell(float fOffset);                // shell with single thickness
public Voxels voxShell(float fNegOffsetMM, float fPosOffsetMM, float fSmoothInnerMM = 0f);

Filters (experimental)

public void Gaussian(float fSizeMM); // Gaussian blur
public void Median(float fSizeMM);   // median filter
public void Mean(float fSizeMM);     // mean filter

Rendering into existing field

public void RenderMesh(in Mesh msh);                                  // union mesh into field
public void RenderImplicit(in IImplicit xImp, in BBox3 oBounds);      // overwrite via SDF
public void IntersectImplicit(in IImplicit xImp);                     // mask existing voxels
public Voxels voxIntersectImplicit(in IImplicit xImp);
public void RenderLattice(in Lattice lat);

Z-slice projection

public void   ProjectZSlice(float fStartZMM, float fEndZMM);
public Voxels voxProjectZSlice(float fStartZMM, float fEndZMM);

Queries

public bool   bIsEqual(in Voxels voxOther);
public void   CalculateProperties(out float fVolumeCubicMM, out BBox3 oBBox);
public BBox3  oCalculateBoundingBox();
public Vector3 vecSurfaceNormal(in Vector3 vecSurfacePoint);
public bool   bClosestPointOnSurface(in Vector3 vecSearch, out Vector3 vecSurfacePoint);
public Vector3 vecClosestPointOnSurface(in Vector3 vecSearch);
public bool   bRayCastToSurface(in Vector3 vecSearch, in Vector3 vecDirection, out Vector3 vecSurfacePoint);
public Vector3 vecRayCastToSurface(in Vector3 vecSearch, in Vector3 vecDirection);

Voxel-grid dimensions and slice extraction

public void GetVoxelDimensions(out int nXOrigin, out int nYOrigin, out int nZOrigin,
                               out int nXSize,   out int nYSize,   out int nZSize);
public void GetVoxelDimensions(out int nXSize,   out int nYSize,   out int nZSize);
public Vector3 vecZSliceOrigin(int nZSlice = 0);
public int     nSliceCount();

public enum ESliceMode { SignedDistance, BlackWhite, Antialiased };

public void GetVoxelSlice(in int nZSlice,           ref ImageGrayScale img,
                          ESliceMode eMode = ESliceMode.SignedDistance);
public void GetInterpolatedVoxelSlice(in float fZSlice, ref ImageGrayScale img,
                          ESliceMode eMode = ESliceMode.SignedDistance);

Vectorize to slices and CLI export (PicoGK_Cli.cs)

public PolySliceStack oVectorize(float fLayerHeight = 0f, bool bUseAbsXYOrigin = false);
public void SaveToCliFile(string strFileName,
                          float fLayerHeight    = 0f,
                          CliIo.EFormat eFormat = CliIo.EFormat.FirstLayerWithContent,
                          bool bUseAbsXYOrigin  = false);
public static Voxels voxFromVdbFile(string strFileName);  // loads first GRID_LEVEL_SET
public void          SaveToVdbFile(string strFileName);

Members

public FieldMetadata m_oMetadata;          // saved/loaded from .vdb

Mesh

Source: PicoGK_Mesh.cs; STL I/O in PicoGK_MeshIo.cs; helpers in PicoGK_MeshMath.cs; voxelization-via-implicit in PicoGK_TriangleVoxelization.cs

Vertex-and-triangle mesh, primarily used as a transport between marching cubes output and STL/voxelization input.

Construction

public Mesh();
public Mesh(in Voxels vox);                              // marching cubes
public Mesh mshCreateTransformed(Vector3 vecScale, Vector3 vecOffset);
public Mesh mshCreateTransformed(Matrix4x4 matTrans);
public Mesh mshCreateMirrored(Vector3 vecPlanePoint, Vector3 vecPlaneNormal);

Vertex / triangle access

public int  nAddVertex(in Vector3 vec);
public void AddVertices(in IEnumerable<Vector3> avecVertices, out int[] anVertexIndex);
public Vector3 vecVertexAt(int nVertex);
public int  nVertexCount();

public int  nAddTriangle(in Triangle t);
public int  nAddTriangle(int A, int B, int C);
public int  nAddTriangle(in Vector3 vecA, in Vector3 vecB, in Vector3 vecC);
public void AddQuad(int n0, int n1, int n2, int n3, bool bFlipped = false);
public void AddQuad(in Vector3 v0, in Vector3 v1, in Vector3 v2, in Vector3 v3, bool bFlipped = false);
public int  nTriangleCount();
public Triangle oTriangleAt(int nTriangle);
public void GetTriangle(int nTriangle, out Vector3 vecA, out Vector3 vecB, out Vector3 vecC);

public void  Append(Mesh msh);                            // appends triangles (no dedup)
public BBox3 oBoundingBox();

Triangle search (PicoGK_MeshMath.cs)

public bool bFindTriangleFromSurfacePoint(Vector3 vecSurfacePoint, out int nTriangle);
public static bool bPointLiesOnTriangle(Vector3 vecP, Vector3 vecA, Vector3 vecB, Vector3 vecC);

Voxelization-via-implicit (PicoGK_TriangleVoxelization.cs)

public Voxels voxVoxelizeHollow(float fThickness); // voxelize as hollow shell

Plus the helper implicits:

public class ImplicitMesh     : IBoundedImplicit { public ImplicitMesh(Mesh msh, float fThickness); }
public class ImplicitTriangle : IBoundedImplicit { public ImplicitTriangle(Vector3 A, Vector3 B, Vector3 C, float fThickness); }
public enum EStlUnit { AUTO, MM, CM, M, FT, IN };

public static Mesh mshFromStlFile(string strFilePath,
                                  EStlUnit  eLoadUnit       = EStlUnit.AUTO,
                                  float     fPostScale      = 1.0f,
                                  Vector3?  vecPostOffsetMM = null);
public static Mesh mshFromStlFile(FileStream oFile, EStlUnit eLoadUnit = EStlUnit.AUTO,
                                  float fPostScale = 1.0f, Vector3? vecPostOffsetMM = null);

public void SaveToStlFile(string strFilePath, EStlUnit eUnit = EStlUnit.AUTO,
                          Vector3? vecOffsetMM = null, float fScale = 1.0f);
public void SaveToStlFile(FileStream oFile,    EStlUnit eUnit = EStlUnit.AUTO,
                          Vector3? vecOffsetMM = null, float fScale = 1.0f);

public string  m_strLoadHeaderData;   // raw STL 80-byte header from last load
public EStlUnit m_eLoadUnits;          // unit detected from `UNITS=` header tag

ASCII STL loading currently throws NotImplementedException; binary STL is fully supported.


Lattice

Source: PicoGK_Lattice.cs

Implicit primitive container: spheres and tapered round-capped beams. Voxelize by passing to new Voxels(lattice) or Voxels.RenderLattice(lat).

public Lattice();

public void AddSphere(in Vector3 vecCenter, float fRadius);

public void AddBeam(in Vector3 vecA, float fRadA,
                    in Vector3 vecB, float fRadB,
                    bool bRoundCap = true);

public void AddBeam(in Vector3 vecA, in Vector3 vecB,
                    float fRadA, float fRadB,
                    bool bRoundCap = true);

ScalarField

Source: PicoGK_ScalarField.cs

A sparse scalar value field on the same voxel grid as Voxels. Implements IImplicit so a populated SDF can be passed anywhere an implicit is accepted.

public ScalarField();
public ScalarField(in ScalarField oSource);
public ScalarField(Voxels oVoxels);                                 // SDF from voxels
public ScalarField(Voxels oVoxels, float fValue, float fSdThreshold = 0.5f);

public void  SetValue(Vector3 vecPosition, float fValue);
public bool  bGetValue(Vector3 vecPosition, out float fValue);
public void  RemoveValue(Vector3 vecPosition);

public void  GetVoxelDimensions(out int nXOrigin, out int nYOrigin, out int nZOrigin,
                                out int nXSize,   out int nYSize,   out int nZSize);
public void  GetVoxelDimensions(out int nXSize, out int nYSize, out int nZSize);
public void  GetVoxelSlice(in int nZSlice, ref ImageGrayScale img);

public void  TraverseActive(ITraverseScalarField xTraverse);

public float fSignedDistance(in Vector3 vecPosition);  // IImplicit impl
public BBox3 oBoundingBox();

public FieldMetadata m_oMetadata;

Companion callback interface:

public interface ITraverseScalarField
{
    void InformActiveValue(in Vector3 vecPosition, float fValue);
}

VectorField

Source: PicoGK_VectorField.cs

Sparse 3D vector field on the voxel grid. Useful for storing gradients, surface normals, or per-voxel directions.

public VectorField();
public VectorField(in VectorField oSource);
public VectorField(Voxels oVoxels);                                 // gradient field
public VectorField(Voxels oVoxels, Vector3 vecValue, float fSdThreshold = 0.5f);

public void SetValue(Vector3 vecPosition, Vector3 vecValue);
public bool bGetValue(Vector3 vecPosition, out Vector3 vecValue);
public void RemoveValue(Vector3 vecPosition);

public void TraverseActive(ITraverseVectorField xTraverse);

public FieldMetadata m_oMetadata;
public interface ITraverseVectorField
{
    void InformActiveValue(in Vector3 vecPosition, in Vector3 vecValue);
}

Implicit interfaces

Source: PicoGK_Voxels.cs (top of file)

public interface IImplicit
{
    float fSignedDistance(in Vector3 vec); // negative = inside, 0 = surface, positive = outside
}

public interface IBoundedImplicit : IImplicit
{
    BBox3 oBounds { get; }
}

ScalarField, ImplicitMesh, and ImplicitTriangle all implement these interfaces.


FieldMetadata

Source: PicoGK_FieldMetadata.cs

A typed key-value table attached to every Voxels, ScalarField, and VectorField. The contents are persisted into .vdb files. PicoGK reserves field names beginning with PicoGK., class, name, and file_; attempts to write those throw FieldAccessException.

public interface IFieldWithMetadata { FieldMetadata oMetaData(); }

public partial class FieldMetadata
{
    public enum EType { UNKNOWN = -1, STRING = 0, FLOAT, VECTOR };

    public int    nCount();
    public bool   bGetNameAt(int nIndex, out string strValueName);
    public EType  eTypeAt(string strName);
    public string strTypeAt(string strName);
    public string strTypeName(EType eType);

    public bool bGetValueAt(string strFieldName, out string strValue);
    public bool bGetValueAt(string strFieldName, out float  fValue);
    public bool bGetValueAt(string strFieldName, out Vector3 vecValue);

    public void SetValue(string strFieldName, string  strValue);
    public void SetValue(string strFieldName, float   fValue);
    public void SetValue(string strFieldName, Vector3 vecValue);

    public void RemoveValue(string strFieldName);

    public override string? ToString();
}

OpenVdbFile

Source: PicoGK_OpenVdbFile.cs

Container for OpenVDB .vdb files holding multiple fields of mixed types (Voxels, ScalarField, VectorField). Field order is not preserved by OpenVDB. Retrieve by name when you have multiple.

public enum EFieldType { Unsupported = -1, Voxels = 0, ScalarField = 1, VectorField = 2 }

public OpenVdbFile();                         // empty
public OpenVdbFile(string strFileName);       // load from file
public void SaveToFile(string strFileName);

// Add fields
public int nAdd(Voxels      vox,    string strFieldName = "");
public int nAdd(ScalarField oField, string strFieldName = "");
public int nAdd(VectorField oField, string strFieldName = "");

// Get fields by index or by name
public Voxels      voxGet(int nIndex);
public Voxels      voxGet(string strName);
public ScalarField oGetScalarField(int nIndex);
public ScalarField oGetScalarField(string strName);
public VectorField oGetVectorField(int nIndex);
public VectorField oGetVectorField(string strName);
public IFieldWithMetadata xField(int nIndex);

// Inspection
public int        nFieldCount();
public string     strFieldName(int nIndex);
public EFieldType eFieldType(int nIndex);
public string     strFieldType(int nIndex);

// PicoGK-specific metadata helpers
public bool  bIsPicoGKCompatible();         // checks PicoGK.VoxelSize metadata
public float fPicoGKVoxelSizeMM();           // returns size from metadata, or 0

Slicing: PolyContour, PolySlice, PolySliceStack

Source: PicoGK_Slice.cs

2D contour primitives produced by Voxels.oVectorize (marching squares on SDF slices).

PolyContour

public enum EWinding { UNKNOWN, CLOCKWISE, COUNTERCLOCKWISE }
public static string  strWindingAsString(EWinding eWinding);
public static EWinding eDetectWinding(List<Vector2> oVertices);

public PolyContour(IEnumerable<Vector2> oVertices, EWinding eWinding = EWinding.UNKNOWN);
public void          AddVertex(Vector2 vec);
public void          DetectWinding();
public EWinding      eWinding();
public List<Vector2> oVertices();
public void          Close();
public void          AsSvgPolyline(out string str);
public void          AsSvgPath(out string str);
public BBox2         oBBox();
public int           nCount();
public Vector2       vecVertex(int n);

PolySlice

public PolySlice(float fZPos);
public void  AddContour(PolyContour oPoly);
public bool  bIsEmpty();
public void  Close();
public void  SaveToSvgFile(string strPath, bool bSolid, BBox2? oBBoxToUse = null);

public static PolySlice oFromSdf(Image img, float fZPos, Vector2 vecOffset, float fScale);

public float       fZPos();
public BBox2       oBBox();
public int         nContours();
public PolyContour oContourAt(int i);

PolySliceStack

public PolySliceStack();
public PolySliceStack(List<PolySlice> oSlices);
public void  AddSlices(List<PolySlice> oSlices);

// Visualize all contours in the viewer (color by winding direction)
public void  AddToViewer(Viewer oViewer,
                         ColorFloat? clrOutside    = null,
                         ColorFloat? clrInside     = null,
                         ColorFloat? clrDegenerate = null,
                         int nGroup = 0);

public int       nCount();
public PolySlice oSliceAt(int n);
public BBox3     oBBox();

CLI file I/O

Source: PicoGK_Cli.cs

CLI is the Common Layer Interface format used by industrial Laser Powder Bed Fusion 3D printers.

public class CliIo
{
    public enum EFormat { UseEmptyFirstLayer, FirstLayerWithContent };

    public class Result
    {
        public PolySliceStack oSlices;
        public BBox3   oBBoxFile;
        public bool    bBinary;
        public float   fUnitsHeader;
        public bool    b32BitAlign;
        public UInt32  nVersion;
        public string  strHeaderDate;
        public UInt32  nLayers;
        public string  strWarnings;
    }

    public static void   WriteSlicesToCliFile(PolySliceStack oSlices,
                                              string strFilePath,
                                              EFormat eFormat,
                                              string strDate     = "",
                                              float  fUnitsInMM  = 0.0f);
    public static Result oSlicesFromCliFile(string strFilePath);
}

Voxels.SaveToCliFile (above) is the convenient wrapper.


PolyLine

Source: PicoGK_PolyLine.cs

A colored 3D polyline used for viewer overlays (axes, vector arrows, contour outlines).

public PolyLine(ColorFloat clr);
public int     nAddVertex(in Vector3 vec);
public void    Add(IEnumerable<Vector3> avec);
public int     nVertexCount();
public Vector3 vecVertexAt(int nIndex);
public void    GetColor(out ColorFloat clr);
public BBox3   oBoundingBox();

// Glyph helpers — call after building the line
public void AddArrow(float fSizeMM = 1.0f, Vector3? _vecDir = null); // arrow at last vertex
public void AddCross(float fSizeMM = 1.0f);                          // XYZ cross at last vertex

Image and TGA

Source: PicoGK_Image.cs; TGA in PicoGK_ImageIo.cs

PicoGK ships its own minimal image abstraction so the runtime is free of any dependence on a system image library.

Image abstract base

public abstract partial class Image
{
    public enum EType { BW, GRAY, COLOR };
    public readonly int nWidth;
    public readonly int nHeight;
    public readonly EType eType;

    public abstract ColorFloat clrValue(int x, int y);
    public abstract float      fValue  (int x, int y);
    public abstract bool       bValue  (int x, int y);

    public abstract void SetValue(int x, int y, in ColorFloat clr);
    public abstract void SetValue(int x, int y, float fGray);
    public abstract void SetValue(int x, int y, bool  bValue);

    public virtual byte byGetValue(int x, int y);
    public virtual void SetValue (int x, int y, byte byValue);

    public virtual ColorBgr24  sGetBgr24 (int x, int y);
    public virtual ColorBgra32 sGetBgra32(int x, int y);
    public virtual ColorRgb24  sGetRgb24 (int x, int y);
    public virtual ColorRgba32 sGetRgba32(int x, int y);

    public virtual void SetBgr24 (int x, int y, ColorBgr24  sClr);
    public virtual void SetBgra32(int x, int y, ColorBgra32 sClr);
    public virtual void SetRgb24 (int x, int y, ColorRgb24  sClr);
    public virtual void SetRgba32(int x, int y, ColorRgba32 sClr);

    public ColorFloat clrGetAtNormalized(float fTX, float fTY); // bilinear, 0..1 coords

    // Bresenham line drawing (color, grayscale, B/W)
    public void DrawLine(int x0, int y0, int x1, int y1, ColorFloat clr);
    public void DrawLine(int x0, int y0, int x1, int y1, float fGrayscale);
    public void DrawLine(int x0, int y0, int x1, int y1, bool bValue);
}

Concrete image classes

public partial class ImageGrayScale : ImageGrayscaleAbstract
{
    public ImageGrayScale(int _nWidth, int _nHeight);
    public override void  SetValue(int x, int y, float fGray);
    public override float fValue(int x, int y);

    // Render an SDF slice as a color-coded picture (greens inside, grays outside, etc.)
    public ImageColor imgGetColorCodedSDF(float fBackground);

    public static ImageGrayScale imgGetInterpolated(ImageGrayScale a, ImageGrayScale b, float fWeight = 0.5f);

    public float[] m_afValues;    // raw row-major buffer
}

public partial class ImageRgb24  : ImageColorAbstract { public ImageRgb24 (int w, int h); public ImageRgb24 (Image src); }
public partial class ImageRgba32 : ImageColorAbstract { public ImageRgba32(int w, int h); public ImageRgba32(Image src); }
public partial class ImageColor  : ImageColorAbstract { public ImageColor (int w, int h); public ImageColor (Image src); } // ColorFloat backing

public abstract class ImageBWAbstract        : Image { /* bool-backed */ }
public abstract class ImageGrayscaleAbstract : Image { public bool bContainsActivePixels(float fThreshold = 0.0f); }
public abstract class ImageColorAbstract     : Image { /* color-backed */ }

TgaIo: reading and writing TGA files

public class TgaIo
{
    public static void SaveTga    (string strFilename,        in Image img);
    public static void SaveTga    (in BinaryWriter oWriter,    in Image img);
    public static void GetFileInfo(string strFilename,         out Image.EType eType, out int nWidth, out int nHeight);
    public static void GetFileInfo(in BinaryReader oReader,    out Image.EType eType, out int nWidth, out int nHeight);
    public static void LoadTga    (string strFilename,         out Image img);
    public static void LoadTga    (in BinaryReader oReader,    out Image img);
}

Supports 8-bit grayscale and 24-bit BGR color TGAs.


Viewer

Source: PicoGK_Viewer.cs, action queue in PicoGK_ViewerActions.cs, keyboard in PicoGK_ViewerKeyboard.cs, animation in PicoGK_ViewerAnimation.cs, time-lapse in PicoGK_ViewerTimelapse.cs

The Viewer instance is created internally by Library.Go(…) and accessed via Library.oViewer(). Most public methods enqueue actions onto an internal queue processed by the viewer's main thread (bPoll()), so they are safe to call from the user's worker thread.

Construction (called by Library.Go)

public Viewer(string strTitle, Vector2 vecSize, LogFile oLog);

Adding/removing geometry

public void Add   (in Voxels   vox,  int nGroupID = 0);
public void Remove(Voxels       vox);
public void Add   (Mesh         msh, int nGroupID = 0);
public void Remove(Mesh         msh);
public void Add   (PolyLine     poly, int nGroupID = 0);
public void Remove(PolyLine     poly);
public void RemoveAllObjects();

Group control (per integer-keyed group of objects)

public void SetGroupVisible (int nGroupID, bool bVisible);
public void SetGroupStatic  (int nGroupID, bool bStatic);                  // attached to view, not scene
public void SetGroupMaterial(int nGroupID, ColorFloat clr, float fMetallic, float fRoughness);
public void SetGroupMatrix  (int nGroupID, Matrix4x4 mat);                  // local transform

View / camera

public void SetBackgroundColor(ColorFloat clr);
public void AdjustViewAngles  (float fOrbitRelative, float fElevationRelative);
public void SetViewAngles     (float fOrbit, float fElevation);
public void SetFov            (float fAngle);

public float m_fElevation;    // public for read; use SetViewAngles to write
public float m_fOrbit;

Lighting

public void LoadLightSetup(string strFilePath);   // zip with Diffuse.dds + Specular.dds
public void LoadLightSetup(Stream oStream);

Screenshots and time-lapse (PicoGK_ViewerTimelapse.cs)

public void RequestScreenShot(string strScreenShotPath);

public void StartTimeLapse (float fIntervalInMilliseconds, string strPath,
                            string strFileName = "frame_", uint nStartFrame = 0,
                            bool bPaused = false);
public void PauseTimeLapse ();
public void ResumeTimeLapse();
public void StopTimeLapse  ();

Misc

public bool bPoll();              // main-thread pump (called by Library.Go)
public void RequestUpdate();
public bool bIsIdle();
public void LogStatistics();      // logs mesh/triangle/vertex counts and bbox

Keyboard handling (PicoGK_ViewerKeyboard.cs)

public interface IKeyHandler
{
    bool bHandleEvent(Viewer oViewer, EKeys eKey,
                      bool bPressed, bool bShift, bool bCtrl, bool bAlt, bool bCmd);
}

public void AddKeyHandler(IKeyHandler xKeyHandler);

public enum EKeys                    // GLFW key codes — Key_Space, Key_0..9, Key_A..Z,
{                                    // Key_ESC, Key_Enter, Key_Tab, Key_Backspace,
    Key_Space = 32, Key_0 = 48,,   // Key_Insert, Key_Delete, arrow keys, Key_PgUp/Dn,
    Key_F1 = 290,, Key_F12          // Key_Home, Key_End, Key_F1..F12
}

public class KeyAction
{
    public KeyAction(IViewerAction xAction, EKeys eKey,
                     bool bPressed = false,    // true = on press, false = on release
                     bool bShift = false, bool bCtrl = false,
                     bool bAlt = false,   bool bCmd = false);
    public bool bKeyEquals(EKeys eKey, bool bPressed, bool bShift, bool bCtrl, bool bAlt, bool bCmd);
    public void Do(Viewer oViewer);
}

public class KeyHandler : IKeyHandler
{
    public void AddAction(KeyAction oAction);
    public bool bHandleEvent(Viewer, EKeys, bool, bool, bool, bool, bool);
}

Action interface (PicoGK_ViewerActions.cs)

public interface IViewerAction { void Do(Viewer oViewer); }

Bundled actions include RotateToNextRoundAngleAction(EDir) (used by arrow keys to snap orbit by 45 degrees).

Animation hooks (PicoGK_ViewerAnimation.cs)

public class AnimGroupMatrixRotate : Animation.IAction { /* spin a group around an axis */ }
public class AnimViewRotate         : Animation.IAction { /* lerp camera orbit/elevation */ }

public void AddAnimation(Animation oAnim);
public void RemoveAllAnimations();

Animations and Easing

Source: PicoGK_Animation.cs, PicoGK_Easing.cs

public class Animation
{
    public interface IAction { void Do(float fTime); } // fTime is 0..1 eased
    public enum EType { Once, Repeat, Wiggle };

    public Animation(IAction xAction, float fDurationInSeconds,
                     EType eType, Easing.EEasing eEasing);
    public void End();
    public bool bAnimate(float fCurrentTime);
}

public class AnimationQueue
{
    public AnimationQueue();
    public void Clear();
    public bool bPulse();        // call each tick; returns true if redraw needed
    public bool bIsIdle();
    public void Add(Animation oAnim);
}

Easing functions (input and output 0..1):

public class Easing
{
    public static float fEaseSineIn  (float x); public static float fEaseSineOut  (float x); public static float fEaseSineInOut (float x);
    public static float fEaseQuadIn  (float x); public static float fEaseQuadOut  (float x); public static float fEaseQuadInOut (float x);
    public static float fEaseCubicIn (float x); public static float fEaseCubicOut (float x); public static float fEaseCubicInOut(float x);

    public enum EEasing { LINEAR, SINE_IN, SINE_OUT, SINE_INOUT,
                          QUAD_IN, QUAD_OUT, QUAD_INOUT,
                          CUBIC_IN, CUBIC_OUT, CUBIC_INOUT }

    public static float fEasingFunction(float x, EEasing eEasing);
}

Field utilities

Source: PicoGK_FieldUtils.cs

SdfVisualizer

Render SDF scalar fields as color-coded debugging images.

public static ImageColor imgEncodeFromSdf(ScalarField oField,
                                          float fBackgroundValue,
                                          int   nSlice,
                                          ColorFloat? _clrBackground = null,
                                          ColorFloat? _clrSurface    = null,
                                          ColorFloat? _clrInside     = null,
                                          ColorFloat? _clrOutside    = null,
                                          ColorFloat? _clrDefect     = null);

public static bool bDoesSliceContainDefect(ScalarField oField, int nSlice);

public static bool bVisualizeSdfSlicesAsTgaStack(
    ScalarField oField,
    float       fBackgroundValue,
    string      strPath,
    string      strFilePrefix       = "Sdf_",
    bool        bOnlyDefective      = false,
    ColorFloat? _clrBackground = null,
    ColorFloat? _clrSurface    = null,
    ColorFloat? _clrInside     = null,
    ColorFloat? _clrOutside    = null,
    ColorFloat? _clrDefect     = null);

ActiveVoxelCounterScalar

public class ActiveVoxelCounterScalar : ITraverseScalarField
{
    public static int nCount(ScalarField oField);
}

SurfaceNormalFieldExtractor

Extract a VectorField of surface normals from a Voxels, optionally filtered by direction.

public static VectorField oExtract(Voxels   vox,
                                   float    fSurfaceThresholdVx       = 0.5f,
                                   Vector3? vecDirectionFilter        = null,
                                   float    fDirectionFilterTolerance = 0f,
                                   Vector3? vecScaleBy                = null);

VectorFieldMerge

public static void Merge(VectorField oSource, VectorField oTarget);

AddVectorFieldToViewer

Render every Nth vector in a VectorField as an arrow polyline.

public static void AddToViewer(Viewer      oViewer,
                               VectorField oField,
                               ColorFloat  clr,
                               int         nStep   = 10,
                               float       fArrow  = 1f,
                               int         nGroup  = 0);

Geometric primitives: Utils

Source: PicoGK_Utils.cs

public class Utils
{
    public static Mesh mshCreateCube     (BBox3 oBox);
    public static Mesh mshCreateCube     (Vector3? vecScale = null, Vector3? vecOffsetMM = null);
    public static Mesh mshCreateCylinder (Vector3? vecScale = null, Vector3? vecOffsetMM = null, int iSides = 0);
    public static Mesh mshCreateCone     (Vector3? vecScale = null, Vector3? vecOffsetMM = null, int iSides = 0);
    public static Mesh mshCreateGeoSphere(Vector3? vecScale = null, Vector3? vecOffsetMM = null, int iSubdivisions = 0);

    public static void      SetMatrixRow(ref Matrix4x4 mat, uint n, float f1, float f2, float f3, float f4);
    public static Matrix4x4 matLookAt   (Vector3 vecEye, Vector3 vecLookAt);
}

When iSides or iSubdivisions is 0, the helpers automatically pick a tessellation that resolves the shape at the current voxel size.


Filesystem and string helpers

Source: PicoGK_Utils.cs

public static string strStripQuotesFromPath(string strPath);
public static bool   bWaitForFileExistence (string strFile, float fTimeOut = 1000000f);

public static string strHomeFolder        ();
public static string strDocumentsFolder   ();
public static string strProjectRootFolder ();      // 4 levels up from AppContext.BaseDirectory
public static string strPicoGKSourceCodeFolder();  // strProjectRootFolder + "PicoGK"
public static string strExecutableFolder  ();

public static string strDateTimeFilename(in string strPrefix, in string strPostfix); // yyyyMMdd_HHmmss
public static string strShorten(string str, int iMaxCharacters);

TempFolder

public class TempFolder : IDisposable
{
    public TempFolder();              // creates a random folder under system temp
    public string strFolder;          // path
    public void   Dispose();          // deletes files in folder (not subdirs) and removes
}

Logging

Source: PicoGK_Log.cs

public class LogFile : IDisposable
{
    public LogFile(in string strFileName = "", in bool bOutputToConsole = true);
    public void Log(in string strFormat, params object[] args);
    public void LogTime();
    public void Dispose();
}

Library.Log(...) is the normal entry point; the LogFile class is what backs it.


CSV

Source: PicoGK_Csv.cs

public interface IDataTable
{
    int    nMaxColumnCount();
    string strColumnId(int nColumn);
    bool   bFindColumn(string strColumnName, out int nColumn);
    int    nRowCount();
    string strGetAt(int nRow, int nColumn);
    void   SetColumnIds(IEnumerable<string> astrIds);
    void   AddRow(IEnumerable<string> astrData);
}

public class CsvTable : IDataTable
{
    public CsvTable(IEnumerable<string>? astrColumnIDs = null);
    public CsvTable(string strFilePath, string strDelimiters = ",");
    public void Save(string strFilePath, string strDelimiter = ",");

    public void   SetKeyColumn(int nColumn);
    public bool   bGetAt(in string strKey, ref float  fVal);   // strKey is "RowName.ColumnName"
    public bool   bGetAt(in string strKey, ref string strVal);
    // plus IDataTable members
}

Vector3 extensions

Source: PicoGK_VectorExt.cs

public static class Vector3Ext
{
    public static Vector3 vecNormalized(this Vector3 vec);
    public static Vector3 vecMirrored  (this Vector3 vec, Vector3 vecPlanePoint, Vector3 vecPlaneNormalUnitVector);
    public static Vector3 vecTransformed(this Vector3 vec, Matrix4x4 mat);
}

Math types

Source: PicoGK_Types.cs, PicoGK_BBox.cs

These structs have [StructLayout(Sequential, Pack = 1)] because they cross the C/C++ boundary; do not add fields.

Coord: integer voxel coordinates

public struct Coord { public int X, Y, Z; public Coord(int x, int y, int z); }

Triangle: triangle vertex indices

public struct Triangle { public int A, B, C; public Triangle(int a, int b, int c); }

BBox2: 2D axis-aligned bounding box

public struct BBox2
{
    public Vector2 vecMin, vecMax;

    public BBox2();
    public BBox2(float fMinX, float fMinY, float fMaxX, float fMaxY);
    public BBox2(in Vector2 vecSetMin, in Vector2 vecSetMax);

    public bool    bIsEmpty();
    public bool    bContains(Vector2 vec);
    public void    Include(Vector2 vec);
    public void    Include(BBox2 oBox);
    public void    Grow(float fGrowBy);
    public Vector2 vecSize();
    public Vector2 vecCenter();
    public override string ToString();
}

BBox3: 3D axis-aligned bounding box

public struct BBox3
{
    public Vector3 vecMin, vecMax;

    public BBox3();
    public BBox3(float fMinX, float fMinY, float fMinZ, float fMaxX, float fMaxY, float fMaxZ);
    public BBox3(in Vector3 vecSetMin, in Vector3 vecSetMax);

    public Vector3 vecSize();
    public bool    bIsEmpty();
    public bool    bContains(Vector3 vec);
    public void    Include(Vector3 vec);
    public void    Include(BBox3 oBox);
    public void    Include(BBox2 oBox, float fZ = 0.0f);
    public void    Grow(float fGrowBy);
    public Vector3 vecCenter();
    public BBox3   oFitInto(in BBox3 oBounds, out float fScale, out Vector3 vecOffset);
    public Vector3 vecRandomVectorInside(ref Random oRand);
    public BBox2   oAsBoundingBox2();
    public override string ToString();
}

Color types

Source: PicoGK_Color.cs

All color types implicitly convert to/from ColorFloat, so you can pass any of them anywhere a color is expected. ColorFloat additionally accepts hex strings ("FF", "FF80", "FF8800", "FF8800CC").

ColorFloat

public struct ColorFloat
{
    public float R, G, B, A;

    public ColorFloat(string strHex);                 // "#RRGGBB", "RRGGBBAA", "GG", "GGAA"
    public ColorFloat(float fGray, float fAlpha = 1.0f);
    public ColorFloat(float fR, float fG, float fB, float fAlpha = 1.0f);
    public ColorFloat(ColorRgb24 clr);
    public ColorFloat(ColorRgba32 clr);
    public ColorFloat(ColorBgr24 clr);
    public ColorFloat(ColorBgra32 clr);
    public ColorFloat(ColorFloat clr, float fAlphaOverride);
    public ColorFloat(ColorHSV clrHSV);
    public ColorFloat(ColorHLS clrHLS);

    public static implicit operator ColorFloat(string hex);

    public string strAsHexCode();        // shortest valid hex (gray or rgb, plus alpha if not 1)
    public string strAsABGRHexCode();    // always 8 chars in ABGR order
    public override string ToString();   // returns strAsHexCode()

    public static ColorFloat clrWeighted(ColorFloat clr1, ColorFloat clr2, float fWeight);
    public static ColorFloat clrRandom(Random? oRand = null);
}

Byte color structs (interop layouts)

public struct ColorRgb24  { public byte R, G, B;     /* + ctors and implicit op from ColorFloat */ }
public struct ColorRgba32 { public byte R, G, B, A;  /* + ctors and implicit op from ColorFloat */ }
public struct ColorBgr24  { public byte B, G, R;     /* + ctors and implicit op from ColorFloat */ }
public struct ColorBgra32 { public byte B, G, R, A;  /* + ctors and implicit op from ColorFloat */ }

HSV / HLS

public struct ColorHSV
{
    public float H, S, V;
    public ColorHSV(float fH, float fS, float fV);
    public ColorHSV(ColorFloat clr);
    public static implicit operator ColorHSV  (ColorFloat clr);
    public static implicit operator ColorFloat(ColorHSV clrHSV);
}

public struct ColorHLS
{
    public float H, L, S;
    public ColorHLS(float h, float l, float s);
    public ColorHLS(ColorFloat clr);
    public static implicit operator ColorHLS  (ColorFloat clr);
    public static implicit operator ColorFloat(ColorHLS clrHLS);
}

Config

Source: PicoGK__Config.cs

public partial class Config
{
    // The native runtime DLL/dylib name to P/Invoke into.
    // To pin a custom path, replace this constant with the full path including extension.
    public const string strPicoGKLib = "picogk.1.7";
}

Source file map

API area to implementing source file:

API area / class Source file
Voxels (constructors, booleans, offsets, queries, slices) PicoGK_Voxels.cs
Voxels VDB load/save (voxFromVdbFile, SaveToVdbFile) PicoGK_VoxelsIo.cs
Voxels.oVectorize, Voxels.SaveToCliFile, CliIo PicoGK_Cli.cs
Mesh (vertices, triangles, transforms) PicoGK_Mesh.cs
Mesh STL I/O, EStlUnit PicoGK_MeshIo.cs
Mesh.bFindTriangleFromSurfacePoint, bPointLiesOnTriangle PicoGK_MeshMath.cs
ImplicitMesh, ImplicitTriangle, Mesh.voxVoxelizeHollow PicoGK_TriangleVoxelization.cs
Lattice PicoGK_Lattice.cs
ScalarField, ITraverseScalarField PicoGK_ScalarField.cs
VectorField, ITraverseVectorField PicoGK_VectorField.cs
IImplicit, IBoundedImplicit PicoGK_Voxels.cs
FieldMetadata, IFieldWithMetadata PicoGK_FieldMetadata.cs
OpenVdbFile PicoGK_OpenVdbFile.cs
SdfVisualizer, ActiveVoxelCounterScalar, SurfaceNormalFieldExtractor, VectorFieldMerge, AddVectorFieldToViewer PicoGK_FieldUtils.cs
PolyContour, PolySlice, PolySliceStack PicoGK_Slice.cs
PolyLine PicoGK_PolyLine.cs
Image, ImageGrayScale, ImageRgb24, ImageRgba32, ImageColor (and abstract bases) PicoGK_Image.cs
TgaIo PicoGK_ImageIo.cs
Library (Go, headless ctor, runtime accessors, voxel-size conversions) PicoGK_Library.cs
Viewer (add/remove geom, group control, camera, lighting) PicoGK_Viewer.cs
Viewer action queue (IViewerAction, internal *Action classes) PicoGK_ViewerActions.cs
Viewer keyboard (EKeys, IKeyHandler, KeyAction, KeyHandler) PicoGK_ViewerKeyboard.cs
Viewer animations (AnimGroupMatrixRotate, AnimViewRotate, AddAnimation) PicoGK_ViewerAnimation.cs
Viewer time-lapse (StartTimeLapse, Pause, Resume, Stop) PicoGK_ViewerTimelapse.cs
Animation, AnimationQueue PicoGK_Animation.cs
Easing, Easing.EEasing PicoGK_Easing.cs
Utils (mesh primitives, paths, dates, matrices), TempFolder PicoGK_Utils.cs
LogFile PicoGK_Log.cs
IDataTable, CsvTable PicoGK_Csv.cs
Vector3Ext extension methods PicoGK_VectorExt.cs
Coord, Triangle (interop structs) PicoGK_Types.cs
BBox2, BBox3 PicoGK_BBox.cs
ColorFloat, ColorRgb24, ColorRgba32, ColorBgr24, ColorBgra32, ColorHSV, ColorHLS PicoGK_Color.cs
Config.strPicoGKLib (native runtime name) PicoGK__Config.cs
All [DllImport] P/Invoke declarations PicoGK__Interop.cs