Code archives/File Utilities/Milkshape
This code has been declared by its author to be Public Domain code.
Download source code
| |||||
Handle = LoadMS3D("MyModel.ms3d") Examples: http://mitglied.lycos.de/thevertex/download.php?c=media\Milkshape.rar cu olli | |||||
; ------------------------------------------------------------------------------------------- ; Milkshape-Importer 2.3 by Vertex : ; : ; Feature: : ; - Shininess : ; _ Diffuselighting : ; - Alphamaps : ; - Alphatexture : ; - Spheremapping : ; : ; To do: : ; - Including Animation : ; ------------------------------------------------------------------------------------------- ; ------------------------------------------------------------------------------------------- Function LoadMS3D(File$,Parent = 0) Local Stream,Vertices,Triangles,Groups,Materials Local Animation,Joints,Mesh,crtMaterials,crtGroups Stream = ReadFile(File$) If Stream = False Then Return False EndIf If ms3dCheckHeader(Stream) = False Then CloseFile Stream Return False EndIf Vertices = ms3dLoadVertices(Stream) Triangles = ms3dLoadTriangles(Stream) Groups = ms3dLoadGroups(Stream) Materials = ms3dLoadMaterials(Stream) ;Animation = ms3dLoad_Animation(Stream) ;Joints = ms3dLoad_Joints(Stream) CloseFile Stream If Parent Then Mesh = CreateMesh(Parent) Else Mesh = CreateMesh() EndIf crtMaterials = ms3dCreateMaterials(File$,Materials) crtGroups = ms3dCreateGroups(Mesh,Groups,crtMaterials) ms3dCreateVertices(Vertices,Triangles,crtGroups) ms3dCreateTriangles(Triangles,crtGroups) Return Mesh End Function ; ------------------------------------------------------------------------------------------- ; ------------------------------------------------------------------------------------------- Function ms3dCheckHeader(Stream) ; Header : Local I,ID$,Version ;-----------------------: ; : For I = 1 To 10 ; : ID$ = ID$ + Chr$(ReadByte(Stream)) ; ID : Next ; : If ID$ <> "MS3D000000" Then ; : Return False ; : EndIf ; : ; : Version = ReadInt(Stream) ; Version : If Version <> 4 Then ; : Return False ; : EndIf ; : ; : Return True ; : End Function ; : ; ------------------------------------------------------------------------------------------- ; ------------------------------------------------------------------------------------------- Function ms3dLoadVertices(Stream) ; Vertices : Local VertexCount,Vertices,I ;-----------------------; ; : VertexCount = ReadShort(Stream) ; : Vertices = CreateBank(VertexCount * 13 + 2) ; : PokeShort Vertices,0,VertexCount ; : ; : For I = 1 To VertexCount ; : SeekFile Stream,FilePos(Stream) + 1 ; Flags : ReadBytes Vertices,Stream,(I - 1) * 13 + 02,12 ; Position : PokeByte Vertices,(I - 1) * 13 + 14,ReadByte(Stream) ; BoneID : SeekFile Stream,FilePos(Stream) + 1 ; ReferenceCount : Next ; : ; : Return Vertices ; : End Function ; : ; ------------------------------------------------------------------------------------------- ; ------------------------------------------------------------------------------------------- Function ms3dLoadTriangles(Stream) ; Triangles ; Local TriangleCount,Triangles,I ;-----------------------: ; : TriangleCount = ReadShort(Stream) ; : Triangles = CreateBank(TriangleCount * 67 + 2) ; : PokeShort Triangles,0,TriangleCount ; : ; : For I = 1 To TriangleCount ; : SeekFile Stream,FilePos(Stream) + 2 ; Flags : ReadBytes Triangles,Stream,(I - 1) * 67 + 02,6 ; Vertexindices : ReadBytes Triangles,Stream,(I - 1) * 67 + 08,36 ; Vertexnormals : ReadBytes Triangles,Stream,(I - 1) * 67 + 44,24 ; Vertextexcoords : SeekFile Stream,FilePos(Stream) + 1 ; Smoothinggroup : PokeByte Triangles,(I - 1) * 67 + 68,ReadByte(Stream) ; Groupindex : Next ; : ; : Return Triangles ; : End Function ; : ; ------------------------------------------------------------------------------------------- Function ms3dLoadGroups(Stream) ; Groups : Local GroupCount,Groups,I,Dummy ;-----------------------: ; : GroupCount = ReadShort(Stream) ; : Groups = CreateBank(GroupCount + 2) ; : PokeShort Groups,0,GroupCount ; : ; : For I = 1 To GroupCount ; : SeekFile Stream,FilePos(Stream) + 1 ; Flags : SeekFile Stream,FilePos(Stream) + 32 ; Name : Dummy = ReadShort(Stream) ; numTriangle : SeekFile Stream,FilePos(Stream) + (Dummy * 2) ; Triangle : PokeByte Groups,I - 1 + 2,ReadByte(Stream) ; Materialindex : Next ; : ; : Return Groups ; : End Function ; : ; ------------------------------------------------------------------------------------------- ; ------------------------------------------------------------------------------------------- Function ms3dLoadMaterials(Stream) ; Materials : Local MaterialCount,Material,I ;-----------------------: ; : MaterialCount = ReadShort(Stream) ; : Material = CreateBank(MaterialCount * 277 + 2) ; : PokeShort Material,0,MaterialCount ; : ; : For I = 1 To MaterialCount ; : SeekFile Stream,FilePos(Stream) + 32 ; Name : SeekFile Stream,FilePos(Stream) + 16 ; Ambient RGBA : ReadBytes Material,Stream,(I - 1) * 277 + 2,12 ; Difusse RGB : SeekFile Stream,FilePos(Stream) + 4 ; Difusse A : SeekFile Stream,FilePos(Stream) + 16 ; Specular RGBA : SeekFile Stream,FilePos(Stream) + 16 ; Emissive RGBA : PokeFloat Material,(I - 1) * 277 + 14,ReadFloat#(Stream) ; Shininess : PokeFloat Material,(I - 1) * 277 + 18,ReadFloat#(Stream) ; Transparency : PokeByte Material,(I - 1) * 277 + 22,ReadByte(Stream) ; Mode : ReadBytes Material,Stream,(I - 1) * 277 + 023,128 ; Filename : ReadBytes Material,Stream,(I - 1) * 277 + 151,128 ; Alphamap : Next ; : ; : Return Material ; : End Function ; : ; ------------------------------------------------------------------------------------------- ; ------------------------------------------------------------------------------------------- Function ms3dLoadAnimation(Stream) ; Animation : Local Animation ;-----------------------: ; : Animation = CreateBank(12) ; : PokeFloat Animation,0,ReadFloat#(Stream) ; Aniamations FPS : PokeFloat Animation,0,ReadFloat#(Stream) ; Curent time : PokeInt Animation,0,ReadInt(Stream) ; Total frames : ; : End Function ; : ; ------------------------------------------------------------------------------------------- ; ------------------------------------------------------------------------------------------- Function ms3dLoadJoints(Stream) ; Joints : Local JointCount,Joints,I,KeyRotCount,KeyPosCount ;-----------------------: ; : JointCount = ReadShort(Stream) ; : Joints = CreateBank(JointCount * 100 + 2) ; : PokeShort Joints,0,JointCount ; : ; : For I = 1 To JointCount ; : SeekFile Stream,FilePos(Stream) + 1 ; Flags : ReadBytes Joints,Stream,(I - 1) * 100 + 02,32 ; Name : ReadBytes Joints,Stream,(I - 1) * 100 + 34,32 ; Parentname : ReadBytes Joints,Stream,(I - 1) * 100 + 66,12 ; Rotation : ReadBytes Joints,Stream,(I - 1) * 100 + 78,12 ; Position : KeyRotCount = ReadShort(Stream) ; Keycount of rotation : KeyPosCount = ReadShort(Stream) ; Keycount of position : KeyRot = ms3dLoadKeyRot(Stream,KeyRotCount) ; Keyframes of rotation : KeyPos = ms3dLoadKeyPos(Stream,KeyPosCount) ; Keyframes of position : PokeShort Joints,(I - 1) * 100 + 90,KeyRotCount ; : PokeShort Joints,(I - 1) * 100 + 92,KeyPosCount ; : PokeShort Joints,(I - 1) * 100 + 94,KeyRot ; : PokeShort Joints,(I - 1) * 100 + 96,KeyPos ; : Next ; : ; : Return Joints ; : End Function ; : ; ------------------------------------------------------------------------------------------- ; ------------------------------------------------------------------------------------------- Function ms3dLoadKeyRot(Stream,Count) ; KeyRot : Local KeyRot,I ;-----------------------: ; : KeyRot = CreateBank(Count * 16) ; : ; : For I = 1 To Count ; : PokeFloat KeyRot,(I - 1) * 16 + 00,ReadFloat#(Stream) ; Time : ReadBytes KeyRot,Stream,(I - 1) * 16 + 04,12 ; Rotation : Next ; : ; : Return KeyRot ; : End Function ; : ; ------------------------------------------------------------------------------------------- ; ------------------------------------------------------------------------------------------- Function ms3dLoadKeyPos(Stream,Count) ; KeyPos : Local KeyPos,I ;-----------------------: ; : KeyPos = CreateBank(Count * 16) ; : ; : For I = 1 To Count ; : PokeFloat KeyPos,(I - 1) * 16 + 00,ReadFloat#(Stream) ; Time : ReadBytes KeyPos,Stream,(I - 1) * 16 + 04,12 ; Position : Next ; : ; : Return KeyRot ; : End Function ; : ; ------------------------------------------------------------------------------------------- ; ------------------------------------------------------------------------------------------- Function ms3dCreateMaterials(File$,BnkMaterials) Local MaterialCount,Material,I,Mode,J Local Texturefile$,Alphafile$,Texture,Alphamap Local R,G,B,Brush MaterialCount = PeekShort(BnkMaterials,0) Material = CreateBank(MaterialCount * 4) For I = 1 To MaterialCount If PeekByte(BnkMaterials,(I - 1) * 277 + 22) = 128 Then Mode = 64 Else Mode = 1 EndIf For J = (I - 1) * 277 + 023 To (I - 1) * 277 + 151 If PeekByte(BnkMaterials,J) <> 0 Then Texturefile$ = Texturefile$ + Chr$(PeekByte(BnkMaterials,J)) Else Exit EndIf Next Texturefile$ = ms3dGetPath$(File$,Texturefile$) For J = (I - 1) * 277 + 151 To (I - 1) * 277 + 289 If PeekByte(BnkMaterials,J) <> 0 Then Alphafile$ = Alphafile$ + Chr$(PeekByte(BnkMaterials,J)) Else Exit EndIf Next Alphafile$ = ms3dGetPath$(File$,Alphafile$) Texture = LoadTexture(Texturefile$,Mode) R = PeekFloat#(BnkMaterials,(I - 1) * 277 + 02) * 255.0 G = PeekFloat#(BnkMaterials,(I - 1) * 277 + 06) * 255.0 B = PeekFloat#(BnkMaterials,(I - 1) * 277 + 10) * 255.0 If Texture = False Then Brush = CreateBrush(R,G,B) Else FreeTexture Texture Alphamap = LoadTexture(Alphafile$) If Alphamap Then Texture = LoadTexture(Texturefile$,Mode + 2) ms3dSetAlphamap(Texture,Alphamap) FreeTexture Alphamap Else Texture = LoadTexture(Texturefile$,Mode) EndIf Brush = CreateBrush() BrushTexture Brush,Texture BrushColor Brush,R,G,B FreeTexture Texture EndIf BrushShininess Brush,PeekFloat#(BnkMaterials,(I - 1) * 277 + 14) BrushAlpha Brush,PeekFloat#(BnkMaterials,(I - 1) * 277 + 18) PokeInt Material,(I - 1) * 4,Brush Next Return Material End Function ; ------------------------------------------------------------------------------------------- ; ------------------------------------------------------------------------------------------- Function ms3dCreateGroups(Mesh,BnkGroups,BnkMaterial) Local GroupCount,Group,I,Material,Brush,Surface GroupCount = PeekShort(BnkGroups,0) Group = CreateBank(GroupCount * 4) For I = 1 To GroupCount Material = PeekByte(BnkGroups,I + 1) If Material <> 255 Then Brush = PeekInt(BnkMaterial,Material * 4) Surface = CreateSurface(Mesh,Brush) Else Surface = CreateSurface(Mesh) EndIf PokeInt Group,(I - 1) * 4,Surface Next Return Group End Function ; ------------------------------------------------------------------------------------------- ; ------------------------------------------------------------------------------------------- Function ms3dCreateVertices(BnkVertices,BnkTriangles,BnkGroup) Local VertexCount,Group,TriangleCount,I,GI,V0,V1,V2,X#,Y#,Z# Local Surface,NX0#,NY0#,NZ0#,NX1#,NY1#,NZ1#,NX2#,NY2#,NZ2# Local TU0#,TV0#,TU1#,TV1#,TU2#,TV2# VertexCount = PeekShort(BnkVertices,0) Group = CreateBank(VertexCount) TriangleCount = PeekShort(BnkTriangles,0) For I = 1 To TriangleCount GI = PeekByte(BnkTriangles,(I - 1) * 67 + 68) V0 = PeekShort(BnkTriangles,(I - 1) * 67 + 02) V1 = PeekShort(BnkTriangles,(I - 1) * 67 + 04) V2 = PeekShort(BnkTriangles,(I - 1) * 67 + 06) PokeByte Group,V0,GI PokeByte Group,V1,GI PokeByte Group,V2,GI Next For I = 1 To VertexCount X# = PeekFloat#(BnkVertices,(I - 1) * 13 + 02) Y# = PeekFloat#(BnkVertices,(I - 1) * 13 + 06) Z# = PeekFloat#(BnkVertices,(I - 1) * 13 + 10) GI = PeekByte(Group,I - 1) Surface = PeekInt(BnkGroup,GI * 4) AddVertex(Surface,X#,Y#,Z#) Next FreeBank Group For I = 1 To TriangleCount GI = PeekByte(BnkTriangles,(I - 1) * 67 + 68) V0 = PeekShort(BnkTriangles,(I - 1) * 67 + 02) V1 = PeekShort(BnkTriangles,(I - 1) * 67 + 04) V2 = PeekShort(BnkTriangles,(I - 1) * 67 + 06) Surface = PeekInt(BnkGroup,GI * 4) NX0# = PeekFloat#(BnkTriangles,(I - 1) * 67 + 08) NY0# = PeekFloat#(BnkTriangles,(I - 1) * 67 + 12) NZ0# = PeekFloat#(BnkTriangles,(I - 1) * 67 + 16) NX1# = PeekFloat#(BnkTriangles,(I - 1) * 67 + 20) NY1# = PeekFloat#(BnkTriangles,(I - 1) * 67 + 24) NZ1# = PeekFloat#(BnkTriangles,(I - 1) * 67 + 28) NX2# = PeekFloat#(BnkTriangles,(I - 1) * 67 + 32) NY2# = PeekFloat#(BnkTriangles,(I - 1) * 67 + 36) NZ2# = PeekFloat#(BnkTriangles,(I - 1) * 67 + 40) TU0# = PeekFloat#(BnkTriangles,(I - 1) * 67 + 44) TU1# = PeekFloat#(BnkTriangles,(I - 1) * 67 + 48) TU2# = PeekFloat#(BnkTriangles,(I - 1) * 67 + 52) TV0# = PeekFloat#(BnkTriangles,(I - 1) * 67 + 56) TV1# = PeekFloat#(BnkTriangles,(I - 1) * 67 + 60) TV2# = PeekFloat#(BnkTriangles,(I - 1) * 67 + 64) VertexNormal Surface,V0,NX0#,NY0#,NZ0# VertexNormal Surface,V1,NX1#,NY1#,NZ1# VertexNormal Surface,V2,NX2#,NY2#,NZ2# VertexTexCoords Surface,V0,TU0#,TV0# VertexTexCoords Surface,V1,TU1#,TV1# VertexTexCoords Surface,V2,TU2#,TV2# Next End Function ; ------------------------------------------------------------------------------------------- ; ------------------------------------------------------------------------------------------- Function ms3dCreateTriangles(BnkTriangles,BnkGroup) Local TriangleCount,I,GI,V0,V1,V2,Surface TriangleCount = PeekShort(BnkTriangles,0) For I = 1 To TriangleCount GI = PeekByte(BnkTriangles,(I - 1) * 67 + 68) V0 = PeekShort(BnkTriangles,(I - 1) * 67 + 02) V1 = PeekShort(BnkTriangles,(I - 1) * 67 + 04) V2 = PeekShort(BnkTriangles,(I - 1) * 67 + 06) Surface = PeekInt(BnkGroup,GI * 4) AddTriangle Surface,V0,V1,V2 Next End Function ; ------------------------------------------------------------------------------------------- ; ------------------------------------------------------------------------------------------- Function ms3dGetPath$(File1$,File2$) Local I,LastBackshlash If Left$(File2$,1) = "." Or Left$(File2$,1) = "\" Then For I = 1 To Len(File1$) If Mid$(File1$,I,1) = "\" Then LastBackshlash = I Next Return Left$(File1$,LastBackshlash) + File2$ Else Return File2$ EndIf End Function ; ------------------------------------------------------------------------------------------- ; ------------------------------------------------------------------------------------------- Function ms3dSetAlphamap(Texture,Alphamap) Local OldBuffer,TexBuffer,AlphaBuffer Local TexWidth,TexHeight,AlphaWidth Local AlphaHeight,M1#,M2#,X,Y,RGB1,R,G,B Local RGB2,A,ARGB OldBuffer = GraphicsBuffer() TexBuffer = TextureBuffer(Texture) AlphaBuffer = TextureBuffer(Alphamap) TexWidth = TextureWidth(Texture) TexHeight = TextureHeight(Texture) AlphaWidth = TextureWidth(Alphamap) AlphaHeight = TextureHeight(Alphamap) M1# = Float#(TexWidth) / Float#(AlphaWidth) M2# = Float#(TexHeight) / Float#(AlphaHeight) SetBuffer TexBuffer : LockBuffer LockBuffer AlphaBuffer For X = 0 To TexWidth - 1 For Y = 0 To TexHeight - 1 RGB1 = ReadPixelFast(X,Y,TexBuffer) R = (RGB1 And $FF0000) / $10000 G = (RGB1 And $FF00) / $100 B = (RGB1 And $FF) RGB2 = ReadPixelFast(M1# * X,M2# * Y,AlphaBuffer) A = (RGB2 And $FF0000) / $10000 ARGB = A * $1000000 + R * $10000 + G * $100 + B WritePixelFast(X,Y,ARGB,TexBuffer) Next Next UnlockBuffer AlphaBuffer UnlockBuffer : SetBuffer OldBuffer End Function ; ------------------------------------------------------------------------------------------- |
Comments
None.
Code Archives Forum