戻る

Hisui.Spatial: ヒスイでポリゴンデータをラクラク操作

Hisui.Spatial.dll にはポリゴンスープやポリゴンメッシュなどのエンティティが定義されています。 これらのエンティティの使い方を解説します。

これらのエンティティを理解するためには、まず Hisui.Core ネームスペースに定義されている Hisui.Core.IStorage, Hisui.Core.IStorage<T> インターフェイスを理解する必要があります。

Hisui.Spatial.dll に定義されているエンティティ一覧は次の通りです。

エンティティ説明
ITriangleSoup, IPolygonSoup 三角形群または多角形群
ISurface, ICurve 曲面・曲線のインターフェイス
IPolygonMesh ポリゴンメッシュ。
IPolyline 折れ線(ポリライン)
IShell, IPolygonShell ハーフエッジによる位相構造

IStorage, IStorage<T>

Hisui.Core.IStorage<T> インターフェイスは、 int型のID(キー)とT型の値を対応付けるコレクションクラスのインターフェイスです。 キーが int 型に固定された Dictionary クラスと思えば良いでしょう。

メッシュの頂点群やファセット群などは IStorage<T> を利用してコレクションされています。

namespace Hisui.Core {

public struct Item<T>
{
  public int ID ;
  public T Value ;
}

public interface IStorage
{
  int Count { get ; }
  IEnumerable<int> IDs { get ; }
  bool IsReadOnly { get; }
  bool Remove( int id ) ;
  bool Contains( int id ) ;
  void Clear() ;
}

public interface IStorage<T> : IStorage
{
  IEnumerable<T> Values { get ; }
  IEnumerable<Item<T>> Items { get ; }
  T this[int id] { get ; set ; }
  bool Find( int id, out T val ) ;
  int  Put( T val ) ;
}
	
}

ポイント

ITriangleSoup, IPolygonSoup

三角形群や多角形群を表すエンティティです。

トポロジ情報は一切保持していない構造で、面と面の接続関係は保証されていません。 面と面の間には隙間がある可能性もありますし、頂点が隣接面と共有されていない可能性もあります。

namespace Hisui.Spatial
{
  public interface ITriangleSoup
    : Core.IStorage<Triangle>
    , Geom.IBoundary3d
  { }
  
  public interface IPolygonSoup
    : Core.IStorage<IPolygon>
    , Geom.IBoundary3d
  { }
}

インスタンスの生成には Hisui.Core.Factory を利用します。

using Hisui.Spatial;
ITriangleSoup tsoup = Hisui.Core.Factory.NewInstance<ITriangleSoup>();
IPolygonSoup psoup = Hisui.Core.Factory.NewInstance<IPolygonSoup>();

Hisui.Core.Factory はごく簡単なDIコンテナと考えてください。

ISurface, ICurve

ヒスイの曲面、曲線を定義するインターフェイスです。

namespace Hisui.Spatial
{
  public interface ISurface : Core.IBuild, Geom.IBoundary3d
  {
    IPolygonMesh Polygonized { get; }
  }
  
  public interface ICurve : Core.IBuild, Geom.IBoundary3d
  {
    IPolyline Polygonized { get; }
  }
}

この曲面・曲線の定義はヒスイの大きな特徴の一つです。 どちらも Polygonized というプロパティを持っていることが分かります。 つまり、ヒスイでは曲面・曲線を次のように定義していることになります。

CADでよく使用されるパラメトリック曲面(NURBS曲面など)は、パラメータ (u, v) に対して3次元座標 (x, y, z) を一つ対応させるもの、と定義されます。 これに比べてヒスイの曲面の定義は、ポリゴン化できるものは何でも曲面として扱うことが出来るため、 パラメトリック曲面以外の曲面も含めたより広範な曲面が表現できると考えています。

IBuild インターフェイスについては「BreathCount とビルドグラフ」を参照してください。 Build() メソッドが呼ばれると内部で保持している IPolygonMesh オブジェクトが更新されます。

IPolygonMesh

多角形のメッシュ構造を表すエンティティです。 IPolygonSoup と違い、頂点の共有情報が含まれています。 基本的な構造は wavefront obj 形式とよく似ています。

namespace Hisui.Spatial
{
  public interface IPolygonMesh : ISurface
  {
    IPoints Points { get; }
    IDirections Normals { get; }
    IFacets Facets { get; }
    IPolygonSoup Polygons { get; }
  }
}

IPolygonMesh が ISurface を継承していることに注目してください。 ISurface の定義は Polygonized プロパティで IPolygonMesh を返すことでしたから、 IPolygonMesh と ISurface は相補的に定義されていることが分かります。 IPolygonMesh.Polygonized プロパティは、return this と実装されます。

以下に IPoints, IDirections, IFacets の定義を示します。 いずれも Hisui.Core.IStorage<T> を利用して定義されています。

namespace Hisui.Spatial
{
  public interface IPoints
    : Core.IStorage<Geom.Point3d>
    , Geom.IBoundary3d
    , System.ICloneable
  { }
  
  public interface IDirections : Core.IStorage<Geom.Direction3d> { }
  
  public interface IFacets : Core.IStorage<IFacet>  { }
}

インスタンスの生成には Hisui.Core.Factory を利用します。

using Hisui.Spatial;
IPolygonMesh mesh = Hisui.Core.Factory.NewInstance<IPolygonMesh>();

IPolyline

折れ線を表すエンティティです。3次元点座標の列として定義されています。

namespace Hisui.Spatial
{
  public interface IPolyline : ICurve, IEnumerable<Geom.Point3d>
  {
    bool IsLoop { get; }
    int Count { get; }
    Geom.Point3d this[int i] { get; set; }
    void Add( Geom.Point3d p );
    void Clear();
    bool RemoveAt( int i );
  }
}

インスタンスの生成には Hisui.Core.Factory を利用します。

using Hisui.Spatial;
IPolyline polyline = Hisui.Core.Factory.NewInstance<IPolyline>();

IShell, IPolygonShell

ハーフエッジ構造の位相情報を保持するエンティティです。 ハーフエッジ構造とは下図のような位相構造です。 その名の通りハーフエッジは2本の対で1本のエッジを表します。 図のように頂点から隣接頂点へ向かう矢印をイメージすると分かりやすいでしょう。

ハーフエッジは次の IHalfEdge インターフェイスで定義されています。

namespace Hisui.Spatial
{
  public interface IHalfEdge
  {
    IHalfEdge Mate  { get ; }  ... 対になっているハーフエッジ
    IHalfEdge Next  { get ; }  ... 同じループ上の前方向のハーフエッジ
    IHalfEdge Prev  { get ; }  ... 同じループ上の後方向のハーフエッジ
    IHalfEdge Right { get ; }  ... 同じ頂点上の右側のハーフエッジ
    IHalfEdge Left  { get ; }  ... 同じ頂点上の左側のハーフエッジ
    int Vertex      { get ; } 
    int Normal      { get ; } 
    int Edge        { get ; } 
    int Loop        { get ; } 
  }
}

任意の IHalfEdge オブジェクト he に対して次の条件が常に成り立ちます。

この IHalfEdge を用いて IShell は次のように定義されています。

namespace Hisui.Spatial
{
  public interface IShell
  {
    int VertexCount { get; }
    int LoopCount { get; }
    int EdgeCount { get; }

    IEnumerable<IHalfEdge> Vertices { get; }
    IEnumerable<IHalfEdge> Loops { get; }
    IEnumerable<IHalfEdge> Edges { get; }

    IHalfEdge GetVertex( int vid );
    IHalfEdge GetLoop( int lid );
    IHalfEdge GetEdge( int eid );

    IEnumerable<IHalfEdge> AroundVertex( int vid );
    IEnumerable<IHalfEdge> AroundVertex( IHalfEdge he );
    IEnumerable<IHalfEdge> AroundLoop( int lid );
    IEnumerable<IHalfEdge> AroundLoop( IHalfEdge he );

    IHalfEdge InsertVertex( IHalfEdge he );
    IHalfEdge InsertLoop( IHalfEdge he );
    IHalfEdge SplitVertex( IHalfEdge he1, IHalfEdge he2 );
    IHalfEdge SplitLoop( IHalfEdge he1, IHalfEdge he2 );
    IHalfEdge MergeVertex( IHalfEdge he );
    IHalfEdge MergeLoop( IHalfEdge he );
  }
}

IShell は頂点、ループ、エッジの3種類の位相要素を保持しますが、それらへのアクセスはすべて IHalfEdge を介して行われます。 また、IShell には幾何情報が一切含まれていません。 つまり IShell は幾何情報からは完全に独立した純粋な位相情報となっています。

次の IPolygonShell は幾何情報の IPolygonMesh と位相情報の IShell を合わせた構造となっています。

namespace Hisui.Spatial
{
  public interface IPolygonShell
    : IShell
    , IPolygonMesh
    , System.ICloneable
  {
    bool IsLegalTriangleEdgeCollapse( IHalfEdge he );
    bool IsLegalTriangleEdgeSwap( IHalfEdge he );
    bool IsLegalTriangleEdgeSplit( IHalfEdge he );

    IHalfEdge CollapseTriangleEdge( IHalfEdge he );
    IHalfEdge SplitTriangleEdge( IHalfEdge he );
    IHalfEdge SwapTriangleEdge( IHalfEdge he );
    IHalfEdge SplitTriangleFacet( IHalfEdge he );

    IHalfEdge RemoveFacet( int facet );
    IPolygonShell RemoveConnectingShell( IHalfEdge he );
    void Reverse();
  }
}

IShell と IPolygonMesh を多重継承している点がポイントです。 IShell が位相情報を担い、IPolygonMesh が幾何情報を担っています。

CollapseTriangleEdge() などは三角形メッシュ専用のオイラー操作で、ファセットが三角形の場合にしか使用できません。

IPolygonMesh に位相情報を付与するためには次のようにコーディングします。

IPolygonMesh mesh;
IPolygonShell shell = Hisui.Spatial.Util.Convert.ToPolygonShell( mesh );

戻る

Copyright © 2007, 株式会社カタッチ
http://www.quatouch.com