How do you save a mesh made from blitz 3D?

Blitz3D Forums/Blitz3D Beginners Area/How do you save a mesh made from blitz 3D?

RiverRatt(Posted 2004) [#1]
I want to make a 3d terrain generator and have gotten as far as I will go till I have the most important part working, saving.
and mabye exporting.
Does anyone have any suggestions? tuts? Intrist?


fredborg(Posted 2004) [#2]
This might help: http://www.blitzbasic.com/codearcs/codearcs.php?code=866


RiverRatt(Posted 2004) [#3]
Thanks, so where do I plug it in at?

; ModifyTerrain Example
; ---------------------

Graphics3D 640,480
SetBuffer BackBuffer()
SeedRnd MilliSecs()

terra_size=32 ; initial size of terrain, and no. of grids segments, along each side
x_scale=10 ; x scale of terrain
y_scale=50 ; y scale of terrain
z_scale=10 ; z scale of terrain
marker_x=terra_size/2 ; initial x position of marker
marker_z=terra_size/2 ; initial z position of marker
Global camangle





Global camera=CreateCamera()
PositionEntity camera,(terra_size*x_scale)/2,50,0 ; position wherever; just try and get good view of terrain!
RotateEntity camera,30,0,0 ; again, try and get good view of terrain

lite=CreateLight(3)
RotateEntity lite,90,0,0
; Create terrain
Global terra=CreateTerrain(terra_size)
ScaleEntity terra,x_scale,y_scale,z_scale



;change texture button
cycle_tex = 3

;wall_texrure.bmp
wall_tex = LoadTexture("data/wall_texture.bmp")
EntityTexture terra,wall_tex


; Texture terrain
glassgrid_tex=LoadTexture("data/crossgrid.bmp")
;EntityTexture terra,grass_tex
EntityAlpha terra,.5
brownstone_tex=LoadTexture("data/brownstone.bmp")


; Create marker
markerI=CreateSphere()
Global marker=markerI
ScaleEntity marker,1,1,1
EntityColor marker,255,0,0
;Data marker_x
;Data marker_y
; Create array
; texture terrain-1.jpg
terrainA = LoadTexture("data/terrain-1.jpg")
ScaleTexture terrainA,4,4
PointEntity lite,marker

Dim nums(9)


; Fill each element with a random number
For i = 0 To 9
nums(i) = Rand(1,10)
nums(i) = nums(i) + 1
Next

Global tracknum#
Global varX=Rnd(1,5)
Global varY=Rnd(1,5)
Global varZ=Rnd(1,5)
Global Markercube
Markercube = LoadMesh("data/Dir_Box.b3d")
;RotateEntity Markercube,90,0,0
RotateEntity Markercube,0,0,90
ScaleEntity MarkerCube,.5,.5,.5
;ScaleEntity Markercube,4.75,1,4.75
EntityColor MarkerCube,100,0,50
EntityAlpha MarkerCube,.5
Global Mode
Mode = 0

vertex_morph=True

leavelight = 0
cam_turn_speed=0
; Set initial uv scale values
u_scale#=1
v_scale#=1

;start of mainloopVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVVv
While Not KeyDown(1)

;entity free flight mode a second camera?




;light mode l key
If KeyHit (38) = True Then leavelight = leavelight+ 1
If leavelight => 3 leavelight = 1
If leavelight = 1 Then
PositionEntity lite,EntityX(marker),EntityY(marker)+20,EntityZ(marker)+20
;PointEntity lite,marker
End If
;If leavelight = 2 Then


If KeyHit(74) Then ; press + to randomly change the 'cone' of light
LightConeAngles lite, Rand(120),Rand(120)
LightRange lite,Rnd(1000,2000)
PointEntity lite,marker

End If


If KeyHit(79) Then
LightColor lite,Rnd(-255,255),Rnd(-255,255),Rnd(-255,255)
;EntityColor marker,
End If

;check for change of texture

If KeyHit(78) = True Then cycle_tex = cycle_tex + 1
If cycle_tex > 4 Then cycle_tex = 1
If cycle_tex = 1 Then EntityTexture terra,wall_tex
If cycle_tex = 1 Then EntityAlpha terra,.5

If cycle_tex = 2 Then EntityTexture terra,glassgrid_tex
If cycle_tex = 2 Then EntityAlpha terra,.5

If cycle_tex = 3 Then EntityTexture terra,terrainA
If cycle_tex = 3 Then EntityAlpha terra,1

If cycle_tex = 4 Then EntityTexture terra,brownstone_tex
If cycle_tex = 4 Then EntityAlpha terra,1
;If cycle_tex = 4 Then ScaleTexture brownstone_tex,2,2
;up on numberpad = 72
;down on mumberpad = 80
;left on numberpad = 75
;right on mumberpad = 77
If KeyDown( 80 )=True Then u_scale#=u_scale#-0.01
If KeyDown( 72 )=True Then u_scale#=u_scale#+0.01
If KeyDown( 75 )=True Then v_scale#=v_scale#-0.01
If KeyDown( 77 )=True Then v_scale#=v_scale#+0.01

; Scale texture
If cycle_tex = 4 Then ScaleTexture brownstone_tex,u_scale#,v_scale#





;If KeyHit(78)=True Then

; Change marker position values depending on cursor key pressed
If KeyDown(205)=True Then marker_x=marker_x+1
If KeyDown(203)=True Then marker_x=marker_x-1
If KeyDown(208)=True Then marker_z=marker_z-1
If KeyDown(200)=True Then marker_z=marker_z+1

If KeyHit(2) Then
camangle = camangle + 1
End If
If camangle => 6 Then camangle = 1



updatePosition(camera)
;TurnEntity camera,0,0,cam_turn_speed
;if key hit spacebar then remember current marker position for manipulation
;call it marked point m_point

If KeyHit(57)=True Then


;markpoint

;startpoint
Gosub startData
Read somthing$
tracknum#=0+1


;Restore startData

EndIf



;different efects
;different efects ;random terrain
If KeyHit(59) Then
Mode = 1
;get 3 random variables from a function
marker_Vars()
terra_detail=4000

End If

If KeyHit(60)= True Then enable=1-enable

; Enable/disable wireframe rendering
WireFrame enable




If Mode = 3 Then

PositionEntity MarkerCube,EntityX(marker)-1.1,EntityY(marker)+1,EntityZ(marker)-.6
EndIf


; Get terrain height at marker position
marker_y#=TerrainHeight(terra,marker_x,marker_z)

; If A pressed then increase marker_y value and modify terrain
If KeyDown(30)=True
If marker_y#<1 Then marker_y#=marker_y#+0.005
If Mode = 0 Then
ModifyTerrain terra,marker_x,marker_z,marker_y#
EndIf

EndIf
If KeyHit(59)=True Then
Mode = 1
EndIf
If KeyHit(60) = True Then
Mode = 2
EndIf
If KeyHit(61) = True Then
Mode = 3
EndIf
If KeyHit(62)=True Then
Mode = 4
EndIf
If KeyHit(63)=True Then
Mode = 5
EndIf
If Mode = 1 Then
; Position marker, taking into account x, y and z scales of terrain
PositionEntity marker,marker_x*x_scale,marker_y#*y_scale,marker_z*z_scale

End If



If Mode = 3 Then
ModifyTerrain terra,marker_x,marker_z,marker_y#
ModifyTerrain terra,marker_x-1,marker_z-1,marker_y#
ModifyTerrain terra,marker_x-1,marker_z,marker_y#
ModifyTerrain terra,marker_x,marker_z-1,marker_y#
EndIf

If Mode = 4 Then
ModifyTerrain terra,marker_x,marker_z,marker_y#
ModifyTerrain terra,marker_x+1,marker_z+1,marker_y#
ModifyTerrain terra,marker_x+1,marker_z,marker_y#
ModifyTerrain terra,marker_x,marker_z+1,marker_y#
EndIf

If Mode = 5 Then
ModifyTerrain terra,marker_x,marker_z,marker_y#
ModifyTerrain terra,marker_x-1,marker_z-1,marker_y#
ModifyTerrain terra,marker_x-1,marker_z,marker_y#
ModifyTerrain terra,marker_x,marker_z-1,marker_y#

ModifyTerrain terra,marker_x,marker_z,marker_y#
ModifyTerrain terra,marker_x+1,marker_z+1,marker_y#
ModifyTerrain terra,marker_x+1,marker_z,marker_y#
ModifyTerrain terra,marker_x,marker_z+1,marker_y#









EndIf








; If Z pressed then decrease marker_y value and modify terrain
If KeyDown(44)=True
If marker_y#>0 Then marker_y#=marker_y#-0.005
ModifyTerrain terra,marker_x,marker_z,marker_y#
EndIf

; Position marker, taking into account x, y and z scales of terrain
PositionEntity marker,marker_x*x_scale,marker_y#*y_scale,marker_z*z_scale


RenderWorld
Color 150,150,200
Text 0,0,"Use cursor keys to move marker over the terrain"
Text 0,20,"Press A or Z to alter height of terrain at marker's position"
Text 0,40,"Terrain Height: "+ marker_y
Text 0,60,somthing$ + marker_y
Text 0,70,(varX)
Text 0,90,"Drawing_Mode :"+ Mode
Text 0,100,"cycle_tex" + cycle_tex
Text 400,0,"camangle ;" + camangle
Text 400,70,"leavelight" + leavelight
Text 0,120,"marker xyz: x: " +EntityX(marker)+" y: "+ EntityY(marker)+" z: "+EntityZ(marker)
Text 0,140,"MarkerCube xyz: x: " +EntityX(MarkerCube)+" y: "+ EntityY(MarkerCube)+" z: "+EntityZ(MarkerCube)


Flip

Wend

End
.startData
Data 1 + "Tips? Press spacebare to see a small set of instructions."
Data 2 + "keypresses; f1-f5 are drawing modes. + = changetexture "
Data 3 + "- = change lightconeangle,shift = change camera angle"
Data 4 + "f = toggle free light mode, esc = exit,1 on numberpad = changelightcolor"
Data 5 + "control c= toggle freeflight mode or drawing mode."
Data 6 + "It just takes 1 tool to rule! F9 to save"
Data 7 + " for now on data statments shoud be numberd"
Data 8 + " need to figure out how to save a terrain made with this program"
Data 9 + "marker placed"

Function updatePosition(camera)


If camangle=1 Then
PositionEntity camera,EntityX(marker),60,EntityZ(marker)-60
If camangle=1 Then PointEntity camera,marker

EndIf
If camangle = 2 Then
PositionEntity camera,EntityX(marker),120,EntityZ(marker)
If camangle=2 Then PointEntity camera,marker

End If
If camangle = 3 Then
PositionEntity camera,EntityX(marker),80,EntityZ(marker)+30
If camangle=3 Then PointEntity camera,marker

End If
If camangle = 4 Then
PositionEntity camera,EntityX(marker)-30,80,EntityZ(marker)
If camangle=4 Then PointEntity camera,marker

End If
If camangle = 5 Then
cam_speed = cam_speed + 1

PositionEntity camera,EntityX(marker),80,EntityZ(marker) + cam_speed
;RotateEntity camera,0,-180,0

;PointEntity camera,marker



End If

End Function

Function marker_Vars()

varX=Rnd(1,20)
varY=Rnd(1,3)
varZ=Rnd(1,20)
; Here we itterate through all the cells on the terrain grid (switch wireframe on to
; see them) and then make them simply bounce up and down.

;For z = 0 To terra_size -1
;For x = 0 To terra_size-1
;hite# = Sin(TerraY(z,x))
;ModifyTerrain terra,x,z,Abs(hite#/2)+.5,False
;TerraY(z,x) = TerraY(z,x) + 1
;Next
;Next


;ModifyTerrain terra,marker_x+varX,marker_z+varY,marker_y#+varZ

End Function

;Function makebox()
;Mode = 3
;PositionEntity MarkerCube,EntityX(marker)+15,EntityY(marker),EntityZ(marker)+15
;End Function


Neo Genesis10(Posted 2004) [#4]
If you are saving terrain files, it is best you save them as an image file of TerrainSize by TerrainSize. Each pixel is then calculated to be of the same brightness as the height. An example would be a height of 126, so you would plot color 126, 126, 126 at the same coordinates. You cannot use WriteBB3D on terrains - they are NOT true meshes!

Anyway, if you read the code archives correctly, you'd notice there was a function called "WriteBB3D(Filename, mesh)". Make sure you include the "b3dfile.bb" file in your source (used for b3dWriteFloat et al) and call WriteBB3D whenever you need to save the mesh.

Oh, and one other thing - The file it saves is a B3D file, so no special loader is needed to reload it into Blitz. All you need do is use LoadMesh( filename ).

Some untested source code for you...
Function SaveTerrain( terra, filename$ )

	If terra = 0 Return False

	sze = TerrainSize(terra)	; width of terrain
	img = CreateImage(sze, sze)	; Create image used for heightmap

	buff = GraphicsBuffer()
	SetBuffer ImageBuffer(img)

	For x = 0 To (sze - 1)
		For y = 0 To (sze - 1)
			
			hgt = Floor(TerrainHeight#(terra, x, y))
			Color hgt, hgt, hgt
			Plot x, y
		Next
	Next

	SetBuffer buff

	SaveBuffer ImageBuffer(img), filename$

	Return True

End Function



RiverRatt(Posted 2004) [#5]
So if a terrain is not a mesh, what is it?
I have put your code in but I can't see it doing anything.
I am not getting any error messages, thats good.
Is this code to be used with "WriteBB3D(Filename, mesh)" and "b3dfile.bb"? Do I have to change any code in "WriteBB3D(Filename, mesh)" and "b3dfile.bb"? Are you saying that I can only use WriteBB3D if I turn the terrain into a hightmap and save that and blitz will know how to rebuild it by calling LoadMesh( filename )? So its saved as an image but translate int a mesh with these functions?


jfk EO-11110(Posted 2004) [#6]
>>Are you saying that I can only use WriteBB3D if I turn the terrain into a hightmap and save that and blitz will know how to rebuild it by calling LoadMesh( filename )? So its saved as an image but translate int a mesh with these functions? <<
No. you could only use writeBB3D if you turn the terrain into a mesh. Then you could use LoadMesh() to load it later.
If you save it as an Image, you will need to use LoadTerrain later. It is true,Blitz is converting this Image to SOME KIND OF mesh, but it cannot be accessed as a Mesh, instead there is a seperate Command Family for Terrains, check out the command reference > Help.

It isn't that easy to convert a terain to a mesh. personally I wouldn't do this. Imagine a Terrain is made of a heightmap. A heightmap is a BMP with bright and dark zones. the brighter a zone is, the higher will th terrain be at that position. Each pixel of a heightmap is representing one Location on the terrain.

Neos Example is making such a heightmap out of a Terrain and save it as a BMP. Let's assume your Terrain Handle is "terrain", then you can

SaveTerrain( terrain, "myheightmap.bmp" )
...
terrain2=loadterrain("myheightmap.bmp")

Neos Function is useful when you have created the terrain inside Blitz, using the commands CreateTerrain and so on.

It is not very useful if you just loaded the Terrain using LoadTerrain because then you already got that BMP on your harddrive anyway.

The WriteBB3D Example mentioned earlier is useful for real Meshes made with CreateCube, CreateSphere, CreateMesh etc. It can also be used to load a .3DS or .X File and save it as .B3D

Terrains are not real Meshes. Sprites aren't real Meshes too, as well as MD2 Animations. They don't work with the Mesh Command Family (Addmesh, Rotatemesh, Scalemesh, Loadmesh aso.).

Most of these Families DO work with the Entity Command Set, PositionEntity, TurnEntity and so on.