Save scene?
Blitz3D Forums/Blitz3D Programming/Save scene?
| ||
I would like to know how you can save a scene. For example, thinking of scheduled modeling, where a cube, sphere, save it to a file for later reload it is created. Is it possible to do this ?. |
| ||
you mean the meshes, materials, textures, (like with a modeling tool) or the positions orientations scales ? (like with a map editor) in both cases, yes you can. you need to define the structure of your file format and then you know how to write datas (to save it) and how to read datas (bytes, shorts, integers, floats, strings) (to be able to load it and recreate it) |
| ||
Yes. Where Sample? |
| ||
![]() I'm really stuck on this. Some example of how to save a scene ?. For example I add cubes, screens, lights, etc. Save want and then load them. There someone has done this before ?. If I remember correctly Gile [S] does this and it was written in Blitz3D. Please help. |
| ||
There's no default, native way to actually export the 3D world contents. Therefore, you will need to track the different objects and their properties. You may require to retain certain information (for example, Light type, range, colour - camera fog details, primitive shapes, spriteviewmodes etc.) on CREATTION of the objects and store this (i.e. within the custom type) in order to preserve it for later saving/loading. Type OBJECTS Field Entity ;...etc End Type Function SaveScene(FilePath$) Local Count=0 Local T.OBJECTS For T=Each OBJECTS Count=Count+1 Next If Count Local File=WriteFile(FilePath) WriteInt File,Count For T=Each OBJECTS WriteObject(File,T\Entity) Next CloseFile File End If End Function Function LoadScene(FilePath$) ;If required? ClearWorld Delete Each OBJECTS ;----------------------------- Local File=ReadFile(FilePath) Local Count=ReadInt(File) Local Iter For Iter=1 To Count ReadObject(File) Next CloseFile File End Function Function WriteChildren(File,Entity) Local Count=CountChildren(Entity) WriteInt File,Count If (Count) Local Children Local Child For Children=1 To Count Child=GetChild(Entity,Children) WriteObject(Entity,Children,True) Next End If End Function Function WriteObject(File,Entity,Child=False) WriteString File,Lower(EntityClass(Entity)) WriteString File,EntityName(Entity) WriteFloat File,EntityX(File,Not Child) WriteFloat File,EntityY(File,Not Child) WriteFloat File,EntityZ(File,Not Child) WriteFloat File,EntityPitch(File,Not Child) WriteFloat File,EntityYaw(File,Not Child) WriteFloat File,EntityRoll(File,Not Child) Select Lower(EntityClass(Entity)) Case"mesh": ;GetMatElement may be helpful here - but I don't know enough about that command. ;You will need to extract the triangles/vertices/surfaces etc. here ______________________________________________________________________ WriteObjectTexture(File,Entity) Case "terrain": ;Ideally, SaveImage() heightmap may be used instead. WriteInt File,TerrainSize(Entity) WriteObjectTexture(File,Entity) Case "plane": WriteObjectTexture(File,Entity) Case "sprite": ;It might be good to track and store spriteviewmodes and scaling? - The BLITZ3D+ userlib extends B3D with commmands to retrieve these after creation. Default: ;It might be good to track and store light-range and light colours? - The BLITZ3D+ userlib extends B3D with commmands to retrieve these after creation. ;It might be good to track and store range, viewport, fog etc? - The BLITZ3D+ userlib extends B3D with commmands to retrieve these after creation. End Select WriteChildren(File,Entity) End Function Function WriteObjectTexture(File,Entity) Local Layer Local Surface Local Surfaces Local Brush Local Texture Local Layers Local TexturePath$ Local Count=CountSurfaces(Entity) For Surfaces=1 To Count Surface=GetSurface(Entity,Surfaces) Brush=GetSurfaceBrush(Surface) For Layers=0 To 7 Texture=GetBrushTexture(Brush,Layers) TexturePath$=TextureName(Texture) WriteString File,TexturePath FreeTexture Texture FreeBrush Brush Next Next End Function ;It is IMPERATIVE that the readeing format maintains the same structure as writing. Keep a track of the order in which things are read/written... Function ReadObject(File,Child=False,Parent=0) Local Entity Local Class$=Lower(ReadString(File)) Local Name$=ReadString(File) Local X#=ReadFloat(File) Local Y#=ReadFloat(File) Local Z#=ReadFloat(File) Local Pitch#=ReadFloat(File) Local Yaw#=ReadFloat(File) Local Roll#=ReadFloat(File) Select (Class) Case "mesh" Entity=CreateMesh(Parent) ;Here you will read back all the triangles,surfaces/vertices etc______________________________________________________________________ ReadObjectTexture(File,Entity) Case "terrain": ;Ideally, LoadTerrain may be used instead. Local Size=ReadInt(File) Entity=CreateTerrain(Size,Parent) ReadObjectTexture(File,Entity) Case "plane": Entity=CreatePlane() ReadObjectTexture(File,Entity) Case "light": ;It might be good to track and store light-range and light colours? - The BLITZ3D+ userlib extends B3D with commmands to retrieve these after creation. Entity=CreateLight() Case "camera": ;It might be good to track and store range, viewport, fog etc? - The BLITZ3D+ userlib extends B3D with commmands to retrieve these after creation. Entity=CreateCamera() Case "mirror": Entity=CreateMirror(Parent) Case "pivot": Entity=CreatePivot(Parent) Case "sprite": Entity=CreateSprite(Parent) End Select PositionEntity Entity,X,Y,Z,Not(Child) RotateEntity Entity,Pitch,Yaw,Roll,Not(Child) NameEntity Entity,Name Local Children=ReadInt(File) If (Children) Then ReadChildren(File,Entity,Children) If Not(Child) Local T.OBJECTS=New OBJECTS T\Entity=Entity End If End Function Function ReadChildren(File,Entity,Count) Local Children Local Child For Children=1 To Count ; Be wary of memory leaks here, you can only access this child enitty via its parent ReadObject(File,True,Entity) Next End Function Function ReadObjectTexture(File,Entity) Local Layer Local Surface Local Surfaces Local Texture Local Layers Local TexturePath$ Local Brush Local Count=CountSurfaces(Entity) For Surfaces=1 To Count Surface=GetSurface(Entity,Surfaces) For Layers=0 To 7 TexturePath$=TextureName(Texture) If (FileType(TexturePath)=1) Texture=LoadTexture(TexturePath);Paramters must be tracked somewhere ... If Not(Brush) Then Brush=CreateBrush() BrushTexture Brush,Texture,0,Layers End If FreeTexture Texture ; I am hoping this does not affect the texture as applied to Brush - if so, then it should be Free'd afterwards (perhasp using an array of Texture[layer] Next If Brush Then PaintSurface Entity,Brush FreeBrush Brush Brush=0 Next End Function |
| ||
here is what i use for one of my map editor : |
| ||
Thanks guys, I have a starting point to implement this. I have always something new to learn. :) |
| ||
just as a general view: you need to say eg. x=100 and then position the mesh at x. Now you can save x in a textfile, later read x and reposition the mesh. Of course you need to store not only X, But anything: path/filename, texturefilw, pitch yaw roll x,y,z,scale,fx.... to successfully restore the object. Furthermore, you need a list of these multiple params, for a list of objects. you can use arrays, types or banks for that. The easiest may be arrays, like: maxo=65000 dim x#(maxo) ;define params, by user input, or by reading from file: x(zz)=100 ... positionentity mesh(zz), x(zz), y(zz... zz=zz +1; set index to next object ;pseudocode for loading: zz=0 re=readfile("mysaveworld") while not eof(re) file$(zz)=readline(re) x(zz)=readline(re) y(zz)=readline(re) z(zz)=readline(re) mesh(zz)=loadmesh(file$(zz)) positionentity mesh(zz),x(zz),y(zz),z(zz) zz=zz+1 wend closefile re ;and saving: num=zz wr=writefile("mysaveworld") for zz=0 to num-1 writeline wr,file$(zz) writeline wr,x(zz) writeline wr,y(zz) writeline wr,z(zz) next closefile re The best approach is to first make a list of all the properties that need to be stored, by systematicly go trough the command reference for entity and mesh handling. Also, by adding eg. an object descriptor in the first line of an object block/container in savefile, such as "light" you can execute an individual loading/restoring procedure. |
| ||
. |
| ||
This does not work for me, my experiments return extraneous data, I think I'm doing well, but obviously not. Any suggestions? |
| ||
@yue>>you can only write/read lines (strings) in .txt files, if you want to write/read bytes, shorts, integers, floats, strings, you must create a binary file (just replace .txt by .whatyouwant) if you really want to write/read integers/floats values in a .txt file, you need to convert the integer/float to a string before writting it and convert the string to integer/float after reading it. |
| ||
RemiD, i change code on post. I confused. |
| ||
Sample, "Escene.whatyouwant", Yes? |
| ||
"filename.ext" where ".ext" is the extension that you prefer, but try to avoid the already used ones to prevent confusion (not .txt, .decls, .dll, .exe, .com, etc...) it could be mapname.yuemap |
| ||
OK, Thanks You. Problem here. Type TData Field x#, y#, Z# End Type Local c% Local t1.TData = New TData t1\x# = 1.0 t1\y# = 2.0 t1\Z# = 3.0 Local t2.TData = New TData t2\x# = 4.0 t2\y# = 5.0 t2\Z# = 6.0 Function Init_TData.TData( x#,y#,Z# ) Local Da.TData = New TData Da\x# = x# Da\y# = y# Da\Z# = Z# Return Da.TData End Function Local file% = WriteFile("Level.map") For t.TData = Each TData c% = c% + 1 Next If c% Then For t.TData = Each TData WriteInt file%, c% WriteFloat file%,t1\x# WriteFloat file%,t1\y# WriteFloat file%,t1\Z# Next End If CloseFile(file%) Color 255, 0, 0 Print "Save Data.. Ok" Print ( "__________________________________") Print ( "Press Key load data") Delete Each TData WaitKey() Print ( "Data Objetc" ) file% = OpenFile("Level.map") c% = ReadInt( file% ) For n% = 1 To c% x# = ReadFloat(file%) y# = ReadFloat(file%) z# = ReadFloat(file%) Init_TData(x#, y#, z# ) Next For TC.TData = Each TData Print TC\X# Print TC\Y# Next WaitKey() CloseFile file% Delete Each TData Return number error. ![]() |
| ||
![]() Problem here. No return, 1,2,3,4,5,6 :( |
| ||
I was in shock when i learnt blitz3d that u cant actually save what you created.. it seems to me a basic essential thing to be implemented on a so called game engine.. But once you make it right (save map..) it will serve u forever |
| ||
1) Not sure if Blitz3D ever referred to itself as a 'Game Engine', raher as a programming language based on Blitz 2) Everything you create with Blitz3D can and may be saved. 3) Either you save the bb files, the compiled executable, or export relevant data using CreateFile or WriteFile etc. ________________________ @Yue I think this may help: If c% Then WriteInt file%, c%; Keep this outside the loop. For t.TData = Each TData WriteFloat file%,t\x#; Not using t1\ as this refers to a specific instance from earlier. t\ is the current iteration of TData objets WriteFloat file%,t\y# WriteFloat file%,t\Z# Next |