5 axis Cardano suspension (gimbal)

Everything related to 3D programming
User avatar
Psychophanta
Addict
Addict
Posts: 4997
Joined: Wed Jun 11, 2003 9:33 pm
Location: Lípetsk, Russian Federation
Contact:

5 axis Cardano suspension (gimbal)

Post by Psychophanta »

Since there is not a CatchTexture() native function i can not give you here in the code more beautiful textures, however, it is free to modify, of course.
I have disabled collisions and gravity, which is not elegant, but since collisions are not enougth accurated for this kind of things, i had to disable it.

Strike 0 to 4 keys randomly to rotate central body.

Code: Select all

ExamineDesktops()
Global bitplanes.a=DesktopDepth(0),FRX.u=DesktopWidth(0),FRY.u=DesktopHeight(0)
InitEngine3D()
InitSprite():InitKeyboard():InitMouse():InitSound()
OpenScreen(FRX,FRY,bitplanes.a,"Suspensión de Cardano",#PB_Screen_WaitSynchronization,FrecuenciadeMuestreo.u)
Add3DArchive(#PB_Compiler_Home+"examples/3d/Data/Textures",#PB_3DArchive_FileSystem)
Add3DArchive(#PB_Compiler_Home+"examples/3d/Data/Packs/desert.zip",#PB_3DArchive_Zip)
Parse3DScripts()
EnableWorldPhysics(1)
WorldGravity(0.0)
Enumeration
  #Cielo
EndEnumeration
Enumeration Camaras
  #Camara
EndEnumeration
Enumeration Luces
  #Luz
EndEnumeration
Enumeration Texturas
  #Textura
  #CuerpoCentralTextura
  #PosteTextura
  #SueloTextura
EndEnumeration
Enumeration Materiales
  #Material
  #CuerpoCentralMaterial
  #PosteMaterial
  #SueloMaterial
EndEnumeration
Enumeration Mallas
  #AnilloMalla
  #CuerpoCentralMalla
  #PosteMalla
  #SueloMalla
  #AnilloCardano1Malla
  #RodamientosAnilloCardano1Malla
  #AnilloCardano2Malla
  #RodamientosAnilloCardano2Malla
  #AnilloCardano3Malla
  #RodamientosAnilloCardano3Malla
  #AnilloCardano4Malla
  #RodamientosAnilloCardano4Malla
  #AnilloCardano5Malla
  #RodamientosAnilloCardano5Malla
  #AnilloCardano6Malla
  #RodamientosAnilloCardano6Malla
EndEnumeration
Enumeration Entidades
  #Anillo
  #CuerpoCentral
  #Postes
  #AnilloCardano1
  #RodamientosAnilloCardano1
  #AnilloCardano2
  #RodamientosAnilloCardano2
  #AnilloCardano3
  #RodamientosAnilloCardano3
  #AnilloCardano4
  #RodamientosAnilloCardano4
  #AnilloCardano5
  #RodamientosAnilloCardano5
  #AnilloCardano6
  #RodamientosAnilloCardano6
  #Rodamiento
  #Suelo
EndEnumeration
Enumeration Juntas
  #AnilloCardano1Rotor1
  #AnilloCardano1Rotor2
  #AnilloCardano2Rotor1
  #AnilloCardano2Rotor2
  #AnilloCardano3Rotor1
  #AnilloCardano3Rotor2
  #AnilloCardano4Rotor1
  #AnilloCardano4Rotor2
  #PostesRotor1
  #PostesRotor2
EndEnumeration

Procedure AddMesh(mallaorigen.i,mallaobtenida.i,liberar.b=1)
  Protected Dim mallaorigenDataV.PB_MeshVertex(0),Dim mallaorigenDataF.PB_MeshFace(0),Dim mallaobtenidaDataV.PB_MeshVertex(0),Dim mallaobtenidaDataF.PB_MeshFace(0),i.i,maxindex.i
  GetMeshData(mallaorigen.i,0,mallaorigenDataV(),#PB_Mesh_Vertex|#PB_Mesh_UVCoordinate| #PB_Mesh_Normal|#PB_Mesh_Color,0,MeshVertexCount(mallaorigen.i,0)-1)
  GetMeshData(mallaorigen.i,0,mallaorigenDataF(),#PB_Mesh_Face,0,MeshIndexCount(mallaorigen.i,0)-1)
  GetMeshData(mallaobtenida.i,0,mallaobtenidaDataV(),#PB_Mesh_Vertex|#PB_Mesh_UVCoordinate|#PB_Mesh_Normal|#PB_Mesh_Color,0,MeshVertexCount(mallaobtenida.i,0)-1)
  GetMeshData(mallaobtenida.i,0,mallaobtenidaDataF(),#PB_Mesh_Face,0,MeshIndexCount(mallaobtenida.i,0)-1)
  FreeMesh(mallaobtenida.i)
  CreateMesh(mallaobtenida.i,#PB_Mesh_TriangleList,#PB_Mesh_Static)
  For i=0 To ArraySize(mallaobtenidaDataV())
    With mallaobtenidaDataV(i)
    MeshVertexPosition(\x,\y,\z)
    MeshVertexNormal(\NormalX,\NormalY,\NormalZ)
    MeshVertexTextureCoordinate(\u,\v)
    MeshVertexColor(\Color)
    EndWith
  Next
  For i=0 To ArraySize(mallaorigenDataV())
    With mallaorigenDataV(i)
    MeshVertexPosition(\x,\y,\z)
    MeshVertexNormal(\NormalX,\NormalY,\NormalZ)
    MeshVertexTextureCoordinate(\u,\v)
    MeshVertexColor(\Color)
    EndWith
  Next
  For i=0 To ArraySize(mallaobtenidaDataF()) Step 3
    MeshFace(mallaobtenidaDataF(i)\Index,mallaobtenidaDataF(i+1)\Index,mallaobtenidaDataF(i+2)\Index)
    If mallaobtenidaDataF(i)\Index>maxindex:maxindex=mallaobtenidaDataF(i)\Index:EndIf
    If mallaobtenidaDataF(i+1)\Index>maxindex:maxindex=mallaobtenidaDataF(i+1)\Index:EndIf
    If mallaobtenidaDataF(i+2)\Index>maxindex:maxindex=mallaobtenidaDataF(i+2)\Index:EndIf
  Next
  maxindex+1
  For i=0 To ArraySize(mallaorigenDataF()) Step 3
    MeshFace(mallaorigenDataF(i)\Index+maxindex,mallaorigenDataF(i+1)\Index+maxindex,mallaorigenDataF(i+2)\Index+maxindex)
  Next
  FinishMesh(1)
  NormalizeMesh(mallaobtenida.i)
  UpdateMeshBoundingBox(mallaobtenida.i)
  If liberar.b:FreeMesh(mallaorigen.i):EndIf
EndProcedure
Procedure CrearAnillodeSuspensiondeCardano(malla.i,romalla.i,radio.f=0.5,lados.u=111,altura.f=0.08,grosor.f=0.02)
  CreateTube(malla.i,radio.f+grosor.f/2,radio.f-grosor.f/2,altura.f,lados.u,1)
  Protected c.i=1011:While IsMesh(c.i):c.i+Random(10,1):Wend
  CreateTube(c.i,altura.f*2/5,altura.f/8,grosor.f*1.2,12,1):TransformMesh(c.i,(radio.f+grosor.f)/Sqr(2),0,(radio.f+grosor.f)/Sqr(2),1,1,1,0,45,90,0)
  CopyMesh(c.i,romalla.i)
  TransformMesh(c.i,0,0,0,1,1,1,0,180,0,0)
  AddMesh(c.i,romalla.i)
  CopyMesh(romalla.i,c.i)
  TransformMesh(c.i,0,0,0,radio/(radio+2*grosor),radio/(radio+2*grosor),radio/(radio+2*grosor),0,90,0,0)
  AddMesh(c.i,romalla.i)
EndProcedure

CreateLight(#Luz,$EEEEEE,4,4,2,#PB_Light_Point):SetLightColor(#Luz,#PB_Light_SpecularColor,$FFFFFF)
CreateCamera(#Camara,0,0,100,100):MoveCamera(#Camara,0.5,1,1.33,#PB_Absolute):CameraLookAt(#Camara,0,0,0)
;suelo:
LoadTexture(#SueloTextura,"nvidia/dirt_grayrocky_diffusespecular.jpg"):CreateMaterial(#SueloMaterial,TextureID(#SueloTextura))
CreateCube(#Suelomalla,20):TransformMesh(#Suelomalla,0,0,0,1,0.01,1,0,0,0,0):UpdateMeshBoundingBox(#Suelomalla)
CreateEntity(#Suelo,MeshID(#Suelomalla),MaterialID(#SueloMaterial),0,-1.25,0)
CreateEntityBody(#Suelo,#PB_Entity_StaticBody,1.0,0.8,0.3)
;Cielo:
SkyBox(""):SkyDome("",1):AmbientColor($E1E9FD):SkyBox("desert07.jpg")

CreateMaterial(#PosteMaterial,LoadTexture(#PosteTextura,"soil_wall.jpg"))
;RotateMaterial(#PosteMaterial,270,#PB_Material_Fixed,0)
CreateCylinder(#PosteMalla,0.1,1.5,4,1,1):TransformMesh(#PosteMalla,0.4,-0.5,-0.4,1,1,1,0,0,0,0)
CopyMesh(#PosteMalla,200):TransformMesh(#PosteMalla,0,0,0,1,1,1,0,180,0,0)
AddMesh(200,#PosteMalla)
CreateEntity(#Postes,MeshID(#PosteMalla),MaterialID(#PosteMaterial))

CreateSphere(#CuerpoCentralMalla,0.33333333,40,40)
CreateMaterial(#CuerpoCentralMaterial,LoadTexture(#CuerpoCentralTextura,"MRAMOR6X6.jpg"))
CreateEntity(#CuerpoCentral,MeshID(#CuerpoCentralMalla),MaterialID(#CuerpoCentralMaterial))

radio.f=0.358:dista.f=0.037
CrearAnillodeSuspensiondeCardano(#AnilloCardano1Malla,#RodamientosAnilloCardano1Malla,radio+dista.f*0):UpdateMeshBoundingBox(#AnilloCardano1Malla)
CrearAnillodeSuspensiondeCardano(#AnilloCardano2Malla,#RodamientosAnilloCardano2Malla,radio+dista.f*1):TransformMesh(#AnilloCardano2Malla,0,0,0,1,1,1,0,90,0,0):TransformMesh(#RodamientosAnilloCardano2Malla,0,0,0,1,1,1,0,90,0,0):UpdateMeshBoundingBox(#AnilloCardano2Malla)
CrearAnillodeSuspensiondeCardano(#AnilloCardano3Malla,#RodamientosAnilloCardano3Malla,radio+dista.f*2):UpdateMeshBoundingBox(#AnilloCardano3Malla)
CrearAnillodeSuspensiondeCardano(#AnilloCardano4Malla,#RodamientosAnilloCardano4Malla,radio+dista.f*3):TransformMesh(#AnilloCardano4Malla,0,0,0,1,1,1,0,90,0,0):TransformMesh(#RodamientosAnilloCardano4Malla,0,0,0,1,1,1,0,90,0,0):UpdateMeshBoundingBox(#AnilloCardano4Malla)

CreateMaterial(#Material,LoadTexture(#Textura,"glass.png"))
ScaleMaterial(#Material,3,3,0)
CreateEntity(#AnilloCardano1,MeshID(#AnilloCardano1Malla),MaterialID(#Material))
CreateEntity(#RodamientosAnilloCardano1,MeshID(#RodamientosAnilloCardano1Malla),MaterialID(#Material))
AttachEntityObject(#AnilloCardano1,"",EntityID(#RodamientosAnilloCardano1))
CreateEntity(#AnilloCardano2,MeshID(#AnilloCardano2Malla),MaterialID(#Material))
CreateEntity(#RodamientosAnilloCardano2,MeshID(#RodamientosAnilloCardano2Malla),MaterialID(#Material))
AttachEntityObject(#AnilloCardano2,"",EntityID(#RodamientosAnilloCardano2))
CreateEntity(#AnilloCardano3,MeshID(#AnilloCardano3Malla),MaterialID(#Material))
CreateEntity(#RodamientosAnilloCardano3,MeshID(#RodamientosAnilloCardano3Malla),MaterialID(#Material))
AttachEntityObject(#AnilloCardano3,"",EntityID(#RodamientosAnilloCardano3))
CreateEntity(#AnilloCardano4,MeshID(#AnilloCardano4Malla),MaterialID(#Material))
CreateEntity(#RodamientosAnilloCardano4,MeshID(#RodamientosAnilloCardano4Malla),MaterialID(#Material))
AttachEntityObject(#AnilloCardano4,"",EntityID(#RodamientosAnilloCardano4))

CreateEntityBody(#CuerpoCentral,#PB_Entity_SphereBody,1,0.5,0.5):SetEntityAttribute(#CuerpoCentral,#PB_Entity_DisableContactResponse,#True)
CreateEntityBody(#AnilloCardano1,#PB_Entity_BoxBody,1,0.5,0.5):SetEntityAttribute(#AnilloCardano1,#PB_Entity_DisableContactResponse,#True)
CreateEntityBody(#AnilloCardano2,#PB_Entity_BoxBody,1,0.5,0.5):SetEntityAttribute(#AnilloCardano2,#PB_Entity_DisableContactResponse,#True)
CreateEntityBody(#AnilloCardano3,#PB_Entity_BoxBody,1,0.5,0.5):SetEntityAttribute(#AnilloCardano3,#PB_Entity_DisableContactResponse,#True)
CreateEntityBody(#AnilloCardano4,#PB_Entity_BoxBody,1,0.5,0.5):SetEntityAttribute(#AnilloCardano4,#PB_Entity_DisableContactResponse,#True)
CreateEntityBody(#Postes,#PB_Entity_StaticBody,1,0.5,0.5):SetEntityAttribute(#AnilloCardano4,#PB_Entity_DisableContactResponse,#True)

grosor.f=0.02:dir.f=1/Sqr(2)
radio.f=0.5+dista.f*0:desp.f=(radio+grosor)/2*radio/(radio+2*grosor)
HingeJoint(#AnilloCardano1Rotor1,EntityID(#AnilloCardano1),desp,0,-desp,-dir,0,dir,EntityID(#CuerpoCentral),desp,0,-desp,-dir,0,dir)
HingeJoint(#AnilloCardano1Rotor2,EntityID(#AnilloCardano1),-desp,0,desp,dir,0,-dir,EntityID(#CuerpoCentral),-desp,0,desp,dir,0,-dir)
radio.f=0.5+dista.f*1:desp.f=(radio+grosor)/2*radio/(radio+2*grosor)
HingeJoint(#AnilloCardano2Rotor1,EntityID(#AnilloCardano2),desp,0,desp,-dir,0,-dir,EntityID(#AnilloCardano1),desp,0,desp,-dir,0,-dir)
HingeJoint(#AnilloCardano2Rotor2,EntityID(#AnilloCardano2),-desp,0,-desp,dir,0,dir,EntityID(#AnilloCardano1),-desp,0,-desp,dir,0,dir)
radio.f=0.5+dista.f*2:desp.f=(radio+grosor)/2*radio/(radio+2*grosor)
HingeJoint(#AnilloCardano3Rotor1,EntityID(#AnilloCardano3),desp,0,-desp,-dir,0,dir,EntityID(#AnilloCardano2),desp,0,-desp,-dir,0,dir)
HingeJoint(#AnilloCardano3Rotor2,EntityID(#AnilloCardano3),-desp,0,desp,dir,0,-dir,EntityID(#AnilloCardano2),-desp,0,desp,dir,0,-dir)
radio.f=0.5+dista.f*3:desp.f=(radio+grosor)/2*radio/(radio+2*grosor)
HingeJoint(#AnilloCardano4Rotor1,EntityID(#AnilloCardano4),desp,0,desp,-dir,0,-dir,EntityID(#AnilloCardano3),desp,0,desp,-dir,0,-dir)
HingeJoint(#AnilloCardano4Rotor2,EntityID(#AnilloCardano4),-desp,0,-desp,dir,0,dir,EntityID(#AnilloCardano3),-desp,0,-desp,dir,0,dir)
radio.f=0.5+dista.f*4:desp.f=(radio+grosor)/2*radio/(radio+2*grosor)
HingeJoint(#PostesRotor1,EntityID(#Postes),desp,0,-desp,-dir,0,dir,EntityID(#AnilloCardano4),desp,0,-desp,-dir,0,dir)
HingeJoint(#PostesRotor2,EntityID(#Postes),-desp,0,desp,dir,0,-dir,EntityID(#AnilloCardano4),-desp,0,desp,dir,0,-dir)

Repeat
  ExamineKeyboard()
  If KeyboardReleased(#PB_Key_0):ApplyEntityTorqueImpulse(#CuerpoCentral,0.012,-0.017,-0.01,#PB_Local)
  ElseIf KeyboardReleased(#PB_Key_1):ApplyEntityTorqueImpulse(#AnilloCardano1,0.001,0.007,-0.01,#PB_Local)
  ElseIf KeyboardReleased(#PB_Key_2):ApplyEntityTorqueImpulse(#AnilloCardano2,0.01,0.0,-0.01,#PB_Local)
  ElseIf KeyboardReleased(#PB_Key_3):ApplyEntityTorqueImpulse(#AnilloCardano3,-0.005,0.03,0.014,#PB_Local)
  ElseIf KeyboardReleased(#PB_Key_4):ApplyEntityTorqueImpulse(#AnilloCardano4,-0.05,0.02,-0.014,#PB_Local)
  EndIf
  RenderWorld()
  FlipBuffers():Delay(9)
Until KeyboardPushed(#PB_Key_Escape)
http://www.zeitgeistmovie.com

While world=business:world+mafia:Wend
Will never leave this forum until the absolute bugfree PB :mrgreen: