#Region "C/C++ types in VB.NET"
Imports qword = System.UInt64
Imports dword = System.UInt32
Imports float = System.Single
Imports word = System.UInt16
Imports bool = System.Boolean
#End Region

Partial Public Class NJCM
    Partial Public Class Types
        'The Basic Data Types for dealing with NJCM files
        Public Class XYZCoord
            Implements ICloneable
            Public X As Single
            Public Y As Single
            Public Z As Single
            Sub New()
                Me.X = 0
                Me.Y = 0
                Me.Z = 0
            End Sub
            Sub New(ByVal A As Single, ByVal B As Single, ByVal C As Single)
                Me.X = A
                Me.Y = B
                Me.Z = C
            End Sub
            Public Overrides Function ToString() As String
                Dim tmp As String = Format2(Me.X, "###0.000000") & "," & Format2(Me.Y, "###0.000000") & "," & Format2(Me.Z, "###0.000000")
                Return tmp
            End Function
            Public Function ToString2() As String
                Dim tmp As String = Format(Me.X, "###0.000000") & " " & Format(Me.Y, "###0.000000") & " " & Format(Me.Z, "###0.000000")
                Return tmp
            End Function
            Public Overloads Function Equals(ByVal p As XYZCoord) As Boolean
                'If obj = Nothing Then Return False
                Return (Me = p)
            End Function
            Public Overloads Shared Operator =(ByVal A As XYZCoord, ByVal B As XYZCoord) As Boolean
                Return ((A.X = B.X) _
                        And (A.Y = B.Y) _
                        And (A.Z = B.Z))
            End Operator
            Public Overloads Shared Operator <>(ByVal A As XYZCoord, ByVal B As XYZCoord) As Boolean
                Return Not ((A.X = B.X) _
                        And (A.Y = B.Y) _
                        And (A.Z = B.Z))
            End Operator
            Public Overloads Shared Operator +(ByVal A As XYZCoord, ByVal B As XYZCoord) As XYZCoord
                Return New XYZCoord(A.X + B.X, A.Y + B.Y, A.Z + B.Z)
            End Operator
            Public Overloads Shared Operator +(ByVal A As XYZCoord, ByVal B As Single) As XYZCoord
                Return New XYZCoord(A.X + B, A.Y + B, A.Z + B)
            End Operator
            Public Overloads Shared Operator -(ByVal A As XYZCoord, ByVal B As XYZCoord) As XYZCoord
                Return New XYZCoord(A.X - B.X, A.Y - B.Y, A.Z - B.Z)
            End Operator
            Public Overloads Shared Operator *(ByVal A As XYZCoord, ByVal B As XYZCoord) As XYZCoord
                Return New XYZCoord(A.X * B.X, A.Y * B.Y, A.Z * B.Z)
            End Operator
            Public Overloads Shared Operator *(ByVal A As XYZCoord, ByVal B As Single) As XYZCoord
                Return New XYZCoord(A.X * B, A.Y * B, A.Z * B)
            End Operator
            Public Overloads Shared Operator /(ByVal A As XYZCoord, ByVal B As XYZCoord) As XYZCoord
                Return New XYZCoord(A.X / B.X, A.Y / B.Y, A.Z / B.Z)
            End Operator
            Public Overloads Shared Operator /(ByVal A As XYZCoord, ByVal B As Single) As XYZCoord
                Return New XYZCoord(A.X / B, A.Y / B, A.Z / B)
            End Operator
            Public Function Clone() As Object Implements System.ICloneable.Clone
                Return New XYZCoord(Me.X, Me.Y, Me.Z)
            End Function
            Public Function GetHashValue() As Int32
                Return (FibHash(Me.X) Xor FibHash(Me.Y) Xor FibHash(Me.Z))
            End Function

        End Class
        Public Class UVCoord

            Implements ICloneable

            Public U As Single
            Public V As Single
            Sub New()
                Me.U = 0
                Me.V = 0
            End Sub
            Sub New(ByVal A As Single, ByVal B As Single)
                Me.U = A
                Me.V = B
            End Sub
            Public Overrides Function ToString() As String
                Dim tmp As String = Format(Me.U) & "," & Format(Me.V)
                Return tmp
            End Function
            Public Function ToString2() As String
                Dim tmp As String = Format(Me.U) & " " & Format(Me.V)
                Return tmp
            End Function
            Public Overloads Function Equals(ByVal p As UVCoord) As Boolean
                Return (Me = p)
            End Function
            Public Overloads Shared Operator =(ByVal A As UVCoord, ByVal B As UVCoord) As Boolean
                Return ((A.U = B.U) And (A.V = B.V))
            End Operator
            Public Overloads Shared Operator <>(ByVal A As UVCoord, ByVal B As UVCoord) As Boolean
                Return Not ((A.U = B.U) And (A.V = B.V))
            End Operator
            Public Function Clone() As Object Implements System.ICloneable.Clone
                Return New UVCoord(Me.U, Me.V)
            End Function
        End Class
        Public Class Node
            Public Flags As dword
            Public Model As dword
            Public Translate As New XYZCoord(0, 0, 0)
            Public Rotate As New XYZCoord(0, 0, 0)
            Public Scale As New XYZCoord(1, 1, 1)
            Public Child As dword
            Public Sibling As dword

            Sub New()
                Me.Flags = 0
                Me.Model = 0
                Me.Child = 0
                Me.Sibling = 0
            End Sub

            Sub New(ByVal A As UInt32, ByVal B As UInt32, ByVal C As Types.XYZCoord, ByVal D As Types.XYZCoord, ByVal E As Types.XYZCoord, ByVal F As UInt32, ByVal G As UInt32)
                Me.Flags = A
                Me.Model = B
                Me.Translate = C
                Me.Rotate = D
                Me.Scale = E
                Me.Child = F
                Me.Sibling = G
            End Sub

            ReadOnly Property XLAT() As Boolean
                Get
                    Return Not BitTest(Me.Flags, 0)
                End Get
            End Property
            ReadOnly Property ROT() As Boolean
                Get
                    Return Not BitTest(Me.Flags, 1)
                End Get
            End Property
            ReadOnly Property SCA() As Boolean
                Get
                    Return Not BitTest(Me.Flags, 2)
                End Get
            End Property
            ReadOnly Property DRAW() As Boolean
                Get
                    Return Not BitTest(Me.Flags, 3)
                End Get
            End Property
            ReadOnly Property TRACE() As Boolean
                Get
                    Return Not BitTest(Me.Flags, 4)
                End Get
            End Property
            ReadOnly Property LWO() As Boolean
                Get
                    Return BitTest(Me.Flags, 5)
                End Get
            End Property
            ReadOnly Property SKIP1() As Boolean
                Get
                    Return BitTest(Me.Flags, 6)
                End Get
            End Property
            ReadOnly Property SKIP2() As Boolean
                Get
                    Return BitTest(Me.Flags, 7)
                End Get
            End Property
            ReadOnly Property PushPop()
                Get
                    Return ((Not Me.XLAT) And (Not Me.ROT) And (Not Me.SCA))
                End Get
            End Property
            Function FlagReport() As String
                Dim s As String
                With Me
                    s = "          Flags     "
                    s &= "Translate    : " & MakeYN(.XLAT)
                    s &= " Rotate       : " & MakeYN(.ROT)
                    s &= " Scale        : " & MakeYN(.SCA) & vbCrLf & "                    "
                    s &= "Draw         : " & MakeYN(.DRAW)
                    s &= " Trace        : " & MakeYN(.TRACE)
                    s &= " LWO Eval.    : " & MakeYN(.LWO) & vbCrLf & "                    "
                    s &= "Shape Skip   : " & MakeYN(.SKIP1)
                    s &= " Motion Skip  : " & MakeYN(.SKIP2)
                    s &= " Omit Push/Pop: " & MakeYN(.PushPop)
                End With
                Return s
            End Function
        End Class
        Public Class Model
            Public Vertex As dword
            Public Poly As dword
            Public Center As New XYZCoord
            Public Radius As float

            Sub New()
                Me.Vertex = 0
                Me.Poly = 0
                Me.Center = New Types.XYZCoord(0, 0, 0)
                Me.Radius = 0
            End Sub

            Sub New(ByVal A As UInt32, ByVal B As UInt32, ByVal C As Types.XYZCoord, ByVal D As Single)
                Me.Vertex = A
                Me.Poly = B
                Me.Center = C
                Me.Radius = D
            End Sub
        End Class
        Public Class Chunk
            Public type As Byte
            Public flag As Byte
            Sub New()
                Me.type = 0
                Me.flag = 0
            End Sub
            Sub New(ByVal A As Byte, ByVal B As Byte)
                Me.type = A
                Me.flag = B
            End Sub
            Public Overrides Function ToString() As String
                Dim tmp As String = "Type : " & Format(Me.type, "##0") & " , " & "Flags : " & Format(Me.flag, "##0")
                Return tmp
            End Function
        End Class
        Public Class Matrix
            Public m(4, 4) As float
            Sub New()
                For I As Integer = 0 To 4
                    For J As Integer = 0 To 4
                        Me.m(I, J) = 0
                    Next
                Next
                Me.Identity()
            End Sub
            Sub Identity()
                Me.m(1, 1) = 1.0
                Me.m(2, 2) = 1.0
                Me.m(3, 3) = 1.0
                Me.m(4, 4) = 1.0
            End Sub
            Private Function Format2(ByVal N As Single, Optional ByVal F As String = "") As String
                Dim t As String = Format(N, F)
                If t.Length < F.Length Then t = New String(" ", F.Length - t.Length) & t
                Format2 = t
            End Function
            Public Overrides Function ToString() As String
                Dim i As Integer = 0
                Dim j As Integer = 0
                Dim t As String = ""
                For i = 1 To 4
                    t &= "[ "
                    For j = 1 To 4
                        t &= Format2(Me.m(i, j), "#0.0000") & " "
                    Next
                    t &= " ]" & vbCrLf
                Next
                Return t
            End Function
        End Class
        Public Class RGBA
            Implements ICloneable

            Public R As float
            Public G As float
            Public B As float
            Public A As float

            Sub New()
                Me.R = 0
                Me.G = 0
                Me.B = 0
                Me.A = 0
            End Sub

            Sub New(ByVal Red As Single, ByVal Green As Single, ByVal Blue As Single, ByVal Alpha As Single)
                Me.R = Red
                Me.G = Green
                Me.B = Blue
                Me.A = Alpha
            End Sub
            Public Overloads Shared Operator =(ByVal A As RGBA, ByVal B As RGBA) As Boolean
                Return ((A.R = B.R) _
                        And (A.B = B.B) _
                        And (A.G = B.G) _
                        And (A.A = B.A))
            End Operator
            Public Overloads Shared Operator <>(ByVal A As RGBA, ByVal B As RGBA) As Boolean
                Return Not ((A.R = B.R) _
                        And (A.B = B.B) _
                        And (A.G = B.G) _
                        And (A.A = B.A))
            End Operator
            Public Overloads Function Equals(ByVal p As RGBA) As Boolean
                Return (Me = p)
            End Function
            Public Overrides Function ToString() As String
                Dim tmp As String = Format(Me.R, "0.0000") & "," & Format(Me.G, "0.0000") & "," & Format(Me.B, "0.0000") & "," & Format(Me.A, "0.0000")
                Return tmp
            End Function
            Public Function ToString2() As String
                Dim tmp As String = Format(Me.R, "0.0000") & " " & Format(Me.G, "0.0000") & " " & Format(Me.B, "0.0000") & " " & Format(Me.A, "0.0000")
                Return tmp
            End Function
            Public Function Clone() As Object Implements System.ICloneable.Clone
                Return New RGBA(Me.R, Me.G, Me.B, Me.A)
            End Function
        End Class
        Public Class Material
            Implements ICloneable
            Public Kd As New Types.RGBA(0.8, 0.8, 0.8, 0.0)
            Public Ka As New Types.RGBA(0.2, 0.2, 0.2, 0.0)
            Public Ks As New Types.RGBA(0, 0, 0, 0)
            Public Km As Integer
            Public Fl As Byte
            Sub New()
                Me.Km = -1
                Me.Fl = 0
            End Sub
            Sub New(ByVal Kd As Types.RGBA, ByVal Ka As Types.RGBA, ByVal ks As Types.RGBA, ByVal Km As Integer, ByVal Fl As Byte)
                Me.Kd = Kd
                Me.Ka = Ka
                Me.Ks = ks
                Me.Km = Km
                Me.Fl = Fl
            End Sub
            Public Overloads Function Equals(ByVal p As Material) As Boolean
                Return (Me = p)
            End Function
            Public Overloads Shared Operator =(ByVal A As Material, ByVal B As Material) As Boolean
                Return ((A.Ka = B.Ka) And (A.Kd = B.Kd) And (A.Ks = B.Ks) And (A.Km = B.Km) And (A.Fl = B.Fl))
            End Operator
            Public Overloads Shared Operator <>(ByVal A As Material, ByVal B As Material) As Boolean
                Return Not ((A.Ka = B.Ka) And (A.Kd = B.Kd) And (A.Ks = B.Ks) And (A.Km = B.Km))
            End Operator
            Public Overrides Function ToString() As String
                Dim tmp As String = ""
                tmp &= "Kd = " & Me.Kd.ToString & vbCrLf
                tmp &= "Ka = " & Me.Ka.ToString & vbCrLf
                tmp &= "Ks = " & Me.Ks.ToString & vbCrLf
                tmp &= "Flags = " & HexOut(Me.Fl) & vbCrLf
                tmp &= "Map = " & Me.Km.ToString
                Return tmp
            End Function
            Public Function Clone() As Object Implements System.ICloneable.Clone
                Return New Material(New RGBA(Me.Kd.R, Me.Kd.G, Me.Kd.B, Me.Kd.A), _
                                    New RGBA(Me.Ka.R, Me.Ka.G, Me.Ka.B, Me.Ka.A), _
                                    New RGBA(Me.Ks.R, Me.Ks.G, Me.Ks.B, Me.Ks.A), _
                                    Me.Km, Me.Fl)
            End Function
        End Class
        Public Class FaceNode
            Implements ICloneable
            Public v As XYZCoord
            Public n As XYZCoord
            Public t As UVCoord
            Public b As Integer
            Sub New()
                Me.v = New XYZCoord
                Me.n = New XYZCoord
                Me.t = New UVCoord
                Me.b = -1
            End Sub
            '     Sub New(ByVal A As XYZCoord, ByVal B As XYZCoord, ByVal C As UVCoord)
            '        Me.v = New XYZCoord(A.X, A.Y, A.Z)
            '        Me.n = New XYZCoord(B.X, B.Y, B.Z)
            '        Me.t = New UVCoord(C.U, C.V)
            '       Me.b = -1
            '    End Sub
            Sub New(ByVal Vertex As XYZCoord, ByVal Normal As XYZCoord, ByVal UV As UVCoord, ByVal BoneIndex As Integer)
                Me.v = Vertex.Clone
                Me.n = Normal.Clone
                Me.t = UV.Clone
                Me.b = BoneIndex
            End Sub
            Sub New(ByVal A As Single, ByVal b As Single, ByVal c As Single, ByVal d As Single, ByVal e As Single, ByVal f As Single, ByVal g As Single, ByVal h As Single)
                Me.v = New XYZCoord(A, b, c)
                Me.n = New XYZCoord(d, e, f)
                Me.t = New UVCoord(g, h)
                Me.b = -1
            End Sub
            Public Function Clone() As Object Implements System.ICloneable.Clone
                Return New FaceNode(Me.v.Clone, Me.n.Clone, Me.t.Clone, Me.b)
            End Function
        End Class
        Public Class Face
            Implements ICloneable
            Public A As New FaceNode
            Public B As New FaceNode
            Public C As New FaceNode
            Public Group As Integer
            Public Mi As Integer
            Property MaterialIndex() As Integer
                Get
                    Return Me.Mi
                End Get
                Set(ByVal value As Integer)
                    Me.Mi = value
                End Set
            End Property
            Property GroupNumber() As Integer
                Get
                    Return Me.Group
                End Get
                Set(ByVal value As Integer)
                    Me.Group = value
                End Set
            End Property
            Sub New()
                Me.A = New FaceNode
                Me.B = New FaceNode
                Me.C = New FaceNode
                Me.Group = -1
                Me.Mi = -1
            End Sub
            Sub New(ByVal A As FaceNode, ByVal B As FaceNode, ByVal C As FaceNode, ByVal D As Integer, ByVal E As Integer)
                Me.A = A
                Me.B = B
                Me.C = C
                Me.Group = D
                Me.Mi = E
            End Sub
            Public Overrides Function ToString() As String
                Return "(" & Me.A.v.ToString & ")-(" & Me.B.v.ToString & ")-(" & Me.C.v.ToString & ")"
            End Function
            Public Function Clone() As Object Implements System.ICloneable.Clone
                Return New Face(Me.A.Clone, Me.B.Clone, Me.C.Clone, Me.Group, Me.Mi)
            End Function
        End Class
        Public Class Vertex
            Implements ICloneable

            Public V As XYZCoord
            Public N As XYZCoord
            Public I As Integer
            Public B As Integer
            Public F As Boolean

            Sub New()
                Me.V = New XYZCoord(0, 0, 0)
                Me.N = New XYZCoord(0, 0, 1)
                Me.I = -1
                Me.B = -1
                Me.F = True
            End Sub
            Sub New(ByVal V As XYZCoord, ByVal N As XYZCoord, ByVal I As Integer, ByVal B As Integer, ByVal F As Boolean)
                Me.V = V.Clone
                Me.N = N.Clone
                Me.I = I
                Me.B = B
                Me.F = F
            End Sub
            Public Function Clone() As Object Implements System.ICloneable.Clone
                Return New Vertex(Me.V, Me.N, Me.I, Me.B, Me.F)
            End Function
        End Class
        Public Class Triangle
            Public T(10) As Single
            Sub New()
                For I As Integer = 0 To 10
                    T(I) = 0
                Next
            End Sub
            Sub New(ByVal a As Integer, ByVal b As Integer, ByVal c As Integer, ByVal d As Integer, ByVal e As Integer, ByVal f As Integer, ByVal g As Integer, ByVal h As Integer, ByVal j As Integer, ByVal k As Integer, ByVal l As Integer)
                Me.T(0) = a
                Me.T(1) = b
                Me.T(2) = c
                Me.T(3) = d
                Me.T(4) = e
                Me.T(5) = f
                Me.T(6) = g
                Me.T(7) = h
                Me.T(8) = j
                Me.T(9) = k
                Me.T(10) = l
            End Sub
            Sub New(ByVal A() As Single)
                For I As Integer = 0 To 10
                    Me.T(I) = A(I)
                Next
            End Sub
            Public Overrides Function ToString() As String
                Dim tmp As String = "f "
                tmp &= Format(Me.T(0)) & "/" & Format(Me.T(1)) & "/" & Format(Me.T(2)) & " "
                tmp &= Format(Me.T(3)) & "/" & Format(Me.T(4)) & "/" & Format(Me.T(5)) & " "
                tmp &= Format(Me.T(6)) & "/" & Format(Me.T(7)) & "/" & Format(Me.T(8))
                Return tmp
            End Function
            Public Function ToString2() As String
                Dim tmp As String = ""
                With Me
                    tmp &= .T(0).ToString & " " & .T(1).ToString & " " & .T(2).ToString & " " & .T(3).ToString & " "
                    tmp &= .T(4).ToString & " " & .T(5).ToString & " " & .T(6).ToString & " " & .T(7).ToString & " "
                End With
                Return tmp
            End Function
            Private Function Equality(ByVal A As Triangle, ByVal B As Triangle) As Boolean
                Dim t As Boolean = False
                For I As Integer = 0 To 2
                    For J As Integer = 0 To 2
                        t = t Or (A.T(I * 3) = B.T(J * 3))
                    Next
                Next
                Return t
            End Function
            Public Overrides Function Equals(ByVal obj As Object) As Boolean
                Dim p As Triangle = CType(obj, Triangle)
                Return Equality(Me, p)
            End Function
        End Class
        Public Class FaceGroup
            Implements ICloneable
            Public Start As Integer
            Public Finish As Integer
            Public Mat As Integer
            Sub New()
                Me.Start = -1
                Me.Finish = -1
                Me.Mat = -1
            End Sub
            Sub New(ByVal S As Integer, ByVal F As Integer, ByVal M As Integer)
                Me.Start = S
                Me.Finish = F
                Me.Mat = M
            End Sub
            Public Function Clone() As Object Implements System.ICloneable.Clone
                Return New FaceGroup(Me.Start, Me.Finish, Me.Mat)
            End Function
        End Class
        Public Class Bone
            Implements ICloneable
            Public Parent As Integer
            Public Child As Integer
            Public Sibling As Integer
            Public World As XYZCoord
            Public Position As XYZCoord
            Public Rotation As XYZCoord
            Sub New()
                Me.Parent = -1
                Me.Child = -1
                Me.Sibling = -1
                Me.World = New XYZCoord(0, 0, 0)
                Me.Position = New XYZCoord(0, 0, 0)
                Me.Rotation = New XYZCoord(0, 0, 0)
            End Sub
            Sub New(ByVal P As Integer, ByVal L As XYZCoord, ByVal R As XYZCoord)
                Me.Parent = P
                Me.Child = -1
                Me.Sibling = -1
                Me.World = New Types.XYZCoord(0, 0, 0)
                Me.Position = L.Clone
                Me.Rotation = R.Clone
            End Sub
            Sub New(ByVal P As Integer, ByVal C As Integer, ByVal S As Integer, ByVal L As XYZCoord, ByVal R As XYZCoord)
                Me.Parent = P
                Me.Child = C
                Me.Sibling = S
                Me.World = New XYZCoord(0, 0, 0)
                Me.Position = L.Clone
                Me.Rotation = R.Clone
            End Sub
            Public Overrides Function ToString() As String
                Dim t As String = ""
                t = "Parent=" & Format2(Me.Parent, "##0") & " Position(" & Me.Position.ToString & ") Rotation (" & Me.Rotation.ToString & ")" & vbCrLf
                t &= "      (Child = " & Format(Me.Child) & " , Sibling = " & Format(Me.Sibling) & ")"
                Return t
            End Function
            Function ToString2() As String
                Dim t As String = "P=" & Format2(Me.Parent, "#0") & " C=" & Format2(Me.Child, "#0") & " S=" & Format2(Me.Sibling, "#0") & " W=(" & Me.World.ToString & ")"
                Return t
            End Function
            Public Function Clone() As Object Implements System.ICloneable.Clone
                Return New Bone(Me.Parent, Me.Child, Me.Sibling, Me.Position.Clone, Me.Rotation.Clone)
            End Function
        End Class
        Public Class MVertex
            Implements ICloneable
            Public F As Integer
            Public X As Single
            Public Y As Single
            Public Z As Single
            Public U As Single
            Public V As Single
            Public B As Single
            Sub New()
                With Me
                    .F = 0
                    .X = 0
                    .Y = 0
                    .Z = 0
                    .U = 0
                    .V = 0
                    .B = -1
                End With
            End Sub
            Sub New(ByVal F As Integer, ByVal X As Single, ByVal Y As Single, ByVal Z As Single, ByVal U As Single, ByVal V As Single, ByVal B As Single)
                With Me
                    .F = F
                    .X = X
                    .Y = Y
                    .Z = Z
                    .U = U
                    .V = V
                    .B = B
                End With
            End Sub
            Sub New(ByVal F As Integer, ByVal P As XYZCoord, ByVal T As UVCoord, ByVal B As Integer)
                Me.F = F
                Me.X = P.X
                Me.Y = P.Y
                Me.Z = P.Z
                Me.U = T.U
                Me.V = T.V
                Me.B = B
            End Sub
            Public Overrides Function ToString() As String
                Dim t As String = ""
                t = Format(Me.F, "#0") & " "
                t &= Format(Me.X, "###0.000000") & " " & Format(Me.Y, "###0.000000") & " " & Format(Me.Z, "###0.000000") & " "
                t &= Format(Me.U, "#0.00000") & " " & Format(1 - Me.V, "#0.000000") & " " & Format(Me.B, "##0")
                Return t
            End Function
            Public Overrides Function Equals(ByVal obj As Object) As Boolean
                Dim p As MVertex = CType(obj, MVertex)
                Return ((Me.X = p.X) And (Me.Y = p.Y) And (Me.Z = p.Z) And (Me.U = p.U) And (Me.V = p.V) And (Me.B = p.B))
            End Function
            Public Function Clone() As Object Implements System.ICloneable.Clone
                Return New MVertex(Me.F, Me.X, Me.Y, Me.Z, Me.U, Me.V, Me.B)
            End Function
            Public Overloads Shared Operator =(ByVal A As MVertex, ByVal B As MVertex) As bool
                Return ((A.F = B.F) And (A.X = B.X) And (A.Y = B.Y) And _
                        (A.Z = B.Z) And (A.U = B.U) And _
                        (A.V = B.V) And (A.B = B.B))
            End Operator
            Public Overloads Shared Operator <>(ByVal A As MVertex, ByVal B As MVertex) As bool
                Return Not ((A.F = B.F) And (A.X = B.X) And (A.Y = B.Y) And _
                            (A.Z = B.Z) And (A.U = B.U) And _
                            (A.V = B.V) And (A.B = B.B))
            End Operator
        End Class
        Public Class GBIXEntry
            Implements ICloneable

            Public TexName As String
            Public FileName As String
            Public GBIX As Integer
            Sub New()
                Me.TexName = ""
                Me.FileName = ""
                Me.GBIX = 0
            End Sub
            Sub New(ByVal Tn As String, ByVal Fn As String, ByVal GBIX As Integer)
                Me.TexName = Tn
                Me.FileName = Fn
                Me.GBIX = GBIX
            End Sub
            Public Overrides Function Equals(ByVal obj As Object) As Boolean
                Dim p As GBIXEntry = CType(obj, GBIXEntry)
                Return (Me.GBIX = p.GBIX)
            End Function
            Public Function Clone() As Object Implements System.ICloneable.Clone
                Return New GBIXEntry(Me.TexName, Me.FileName, Me.GBIX)
            End Function
        End Class
        Public Class NJHeader
            Implements ICloneable
            Public ID As String
            Public Nx As Integer

            ReadOnly Property IsEmpty() As Boolean
                Get
                    IsEmpty = (Me.ID = "")
                End Get
            End Property
            Sub New()
                Me.ID = ""
                Me.Nx = -1
            End Sub
            Sub New(ByVal ID As String, ByVal Nx As Integer)
                If ID.Length < 4 Then ID &= New String(Chr(32), ID.Length - 4)
                Me.ID = Strings.Left(ID, 4)
                Me.Nx = Nx
            End Sub
            Public Function Clone() As Object Implements System.ICloneable.Clone
                Return New NJHeader(Me.ID.Clone, Me.Nx)
            End Function
        End Class
    End Class
End Class
