Loading MY3D files from a ZIP ARCHIVE
Loading MY3D files from a ZIP ARCHIVE
I have asked this question in every relevent thread on the board, directly to Niko and ZDiminator, neither of whom replied (or had an answer to give)... surely SOMEONE has loaded a MY3D file from a ziparchive the same way we can load all other meshes/textures etc?
When I try it, an otherwise fine loading mesh (tested both embedded lightmaps and seperate) will refuse to load and logs and error "MAT_HEADER_ID" not found or similar.
I have looked through the source of both my3d and irrlicht to see if a simple thing was missing, all I can see is my3d doesn't have its own "LoadFile" call abstracted and taking into account a zip file. Instead it appears to use more raw calls. I could be wrong.
Anyway, in desperation, I am posting it as a bug (which if you can not load them from zips , it is) to try and give it some attention and hope for a quick fix soon (a patch) or at least a working method that I may have just overlooked. There must be someone out there who is loading my3d meshes (and it's textures/lightmaps) from an irrlicht virtual file system zip archive??? If so.. spill the beanz
cheers
When I try it, an otherwise fine loading mesh (tested both embedded lightmaps and seperate) will refuse to load and logs and error "MAT_HEADER_ID" not found or similar.
I have looked through the source of both my3d and irrlicht to see if a simple thing was missing, all I can see is my3d doesn't have its own "LoadFile" call abstracted and taking into account a zip file. Instead it appears to use more raw calls. I could be wrong.
Anyway, in desperation, I am posting it as a bug (which if you can not load them from zips , it is) to try and give it some attention and hope for a quick fix soon (a patch) or at least a working method that I may have just overlooked. There must be someone out there who is loading my3d meshes (and it's textures/lightmaps) from an irrlicht virtual file system zip archive??? If so.. spill the beanz
cheers
the problem is not in the My3d file itself but in the set texture path parameter:
This parameter can't read inside of zip files and as you know My3d must have the textures next to it besides the lightmaps in the "lightmaps" folder, unlike Quake3 bsp's and pk3 files which are able to read not only the bsp info from the pk3 but the texturing and lightmapping info as well, all in a compressed file. I tried everything without result also. Maybe if my3d would have the texturing info embedded into the format, then we wouldn't require to set the path; the Irrlicht's zip reader would be able to read my3d.
Code: Select all
smgr->getParameters()->setParameter(scene::MY3D_TEXTURE_PATH, "./data/");
Niko, thanks for the reply. The thing is everything else is in an archive, and when distrubting games it is both tidier on the end system and file access is quicker as it is stored contiguously when in an archive which is a big bonus with a lot of assets.
Also, it just looks better. Yes I can get away with leaving the my3d stuff elsewhere in a normal dir (and may have to as my game approaches release quite soon - probably before you have "fixed" it).
As for adding custom archives, that would be nice. Especially if you could stick a little simple encryption in there - nothing special, just enough to stop the general end-user from opening a renamed zip file as a zip and possible deleting (or hacking) contents.
I know this could be done by expanding the code more myself but i'm knee deep in game stuff atm and of course anything official would be far better than I could manage!
Even a zip header scrambler and an ignore header flag in the ziploader may work for a simple "lock" on an archive.
thanks again!
Also, it just looks better. Yes I can get away with leaving the my3d stuff elsewhere in a normal dir (and may have to as my game approaches release quite soon - probably before you have "fixed" it).
As for adding custom archives, that would be nice. Especially if you could stick a little simple encryption in there - nothing special, just enough to stop the general end-user from opening a renamed zip file as a zip and possible deleting (or hacking) contents.
I know this could be done by expanding the code more myself but i'm knee deep in game stuff atm and of course anything official would be far better than I could manage!
Even a zip header scrambler and an ignore header flag in the ziploader may work for a simple "lock" on an archive.
thanks again!
Hi 2All:
There is no any problems in my3d loader, if you want to load my3d scene from *.zip archieve, you must slightly change you code.
Here is a full source of modified My3DExample2 main.cpp file.
Important things:
1) you must compress data directory into my3ddata.zip file (my3d scene stilll places in 'data/' dir, but in archieve)
2) add zip file archive with using full files path
3) we dont need this string parameter
4) all diffuse textures must me in the same dir as *.my3d file
5) all lightmaps must be in 'Lightmaps/' directory in the same dir as *.my3d file
6) load my3d scenes or textures with full file path
Thats all.
[/i]
I test it with Irrlicht 0.12.0 an everything was just fine.
Check this more carefully.
Good luck.
There is no any problems in my3d loader, if you want to load my3d scene from *.zip archieve, you must slightly change you code.
Here is a full source of modified My3DExample2 main.cpp file.
Code: Select all
#include <irrlicht.h>
#include <iostream>
#include <stdio.h>
using namespace irr;
using namespace irr;
using namespace core;
using namespace scene;
using namespace video;
using namespace io;
using namespace gui;
#pragma comment(lib, "Irrlicht.lib")
int main()
{
//-----------------------------------------------------
// ask user for driver
//-----------------------------------------------------
video::E_DRIVER_TYPE driverType;
printf("Please select the driver you want for this example:\n"\
" (a) Direct3D 9.0c\n (b) Direct3D 8.1\n (c) OpenGL 1.2\n"\
" (d) Software Renderer\n (e) NullDevice\n (otherKey) exit\n\n");
char i;
std::cin >> i;
switch(i)
{
case 'a': driverType = video::EDT_DIRECTX9; break;
case 'b': driverType = video::EDT_DIRECTX8; break;
case 'c': driverType = video::EDT_OPENGL; break;
case 'd': driverType = video::EDT_SOFTWARE; break;
case 'e': driverType = video::EDT_NULL; break;
default: return 1;
}
//-----------------------------------------------------
// create device and exit if creation failed
//-----------------------------------------------------
IrrlichtDevice *device =
createDevice(driverType, core::dimension2d<s32>(640, 480),
32, false, true, false, 0
);
if (device == 0)
return 1; // could not create selected driver.
//-----------------------------------------------------
// pointers
//-----------------------------------------------------
video::IVideoDriver* driver = device->getVideoDriver();
scene::ISceneManager* smgr = device->getSceneManager();
gui::IGUIEnvironment* env = device->getGUIEnvironment();
io::IFileSystem *fs = device->getFileSystem();
//----------------------------------------------------------------------
// some features
//-----------------------------------------------------
driver->setTextureCreationFlag(video::ETCF_ALWAYS_32_BIT, true);
driver->setFog(SColor(0,20,20,120),true, 0,12500);
fs->addZipFileArchive("my3ddata.zip", true, false);
//----------------------------------------------------------------------
//load my3d temple scene
//-----------------------------------------------------
smgr->getParameters()->setParameter(scene::MY3D_TEXTURE_PATH, "");
scene::IAnimatedMesh* mesh;
driver->setTextureCreationFlag(video::ETCF_ALWAYS_32_BIT, true);
mesh = smgr->getMesh("data/temple01.my3d");
scene::ISceneNode* test_scene = smgr->addOctTreeSceneNode(mesh->getMesh(0));
test_scene->setPosition( irr::core::vector3df(0,0,0) );
test_scene->setScale( irr::core::vector3df(1,1,1) );
test_scene->setRotation( irr::core::vector3df(0,0,0) );
test_scene->setMaterialFlag(video::EMF_LIGHTING, true);
test_scene->setMaterialFlag(EMF_FOG_ENABLE,true); //enables fog
//-----------------------------------------------------
// my3d skydome
//-----------------------------------------------------
scene::IAnimatedMesh* dome;
dome = smgr->getMesh("data/skydome.my3d");
scene::ISceneNode* domenode = smgr->addOctTreeSceneNode(dome->getMesh(0));
domenode->setPosition( irr::core::vector3df(0,0,0) );
domenode->setScale( irr::core::vector3df(1,1,1) );
domenode->setRotation( irr::core::vector3df(0,0,0) );
domenode->setMaterialFlag(video::EMF_LIGHTING, false);
domenode->getMaterial(0).EmissiveColor.set(0,150,150,255); //makes it emissive
domenode->setMaterialFlag(EMF_FOG_ENABLE,false);
//adding a rotate animator for the dome
scene::ISceneNodeAnimator *domeanim = 0;
domeanim = smgr->createRotationAnimator(core::vector3df(0, 0.05, 0));
domenode->addAnimator(domeanim);
domeanim->drop();
//-----------------------------------------------------
//create sky box
//-----------------------------------------------------
scene::ISceneNode* skyboxNode = 0;
skyboxNode = smgr->addSkyBoxSceneNode(
driver->getTexture("data/rocky_up.jpg"),
driver->getTexture("data/rocky_dn.jpg"),
driver->getTexture("data/rocky_lf.jpg"),
driver->getTexture("data/rocky_rt.jpg"),
driver->getTexture("data/rocky_ft.jpg"),
driver->getTexture("data/rocky_bk.jpg"));
//-----------------------------------------------------
//particle system
//-----------------------------------------------------
scene::IParticleSystemSceneNode* ps;
ps = smgr->addParticleSystemSceneNode(false);
ps->setMaterialFlag(video::EMF_LIGHTING, false);
ps->setPosition(core::vector3df(-5200,850,2000));
ps->setScale(core::vector3df(50,50,50));
ps->setParticleSize(core::dimension2d<f32>(300, 300));
ps->setMaterialTexture(0, driver->getTexture("sprites/particle_white.bmp"));
ps->setMaterialType(video::EMT_TRANSPARENT_VERTEX_ALPHA);
scene::IParticleEmitter* emb = ps->createBoxEmitter(
core::aabbox3d<f32>(-7.00f,0.00f,-7.00f,7.00f,1.00f,7.00f),
core::vector3df(0.00f,0.03f,0.00f),
60,200,
video::SColor(0,255,255,100), video::SColor(0,0,255,0),
100,3400,108);
ps->setEmitter(emb);
emb->drop();
scene::IParticleAffector* paf = ps->createFadeOutParticleAffector(video::SColor(0,0,0,0),1000);
ps->addAffector(paf);
paf->drop();
scene::IParticleAffector* pgaf = ps->createGravityAffector(core::vector3df(0.00f,0.30f,0.00f),2400); ps->addAffector(pgaf);
pgaf->drop();
//-----------------------------------------------------------------------------------------------//
// create sun-light
//-----------------------------------------------------
ILightSceneNode *light = smgr->addLightSceneNode(
0, core::vector3df(25000,15000,0),
video::SColorf(1.0f, 1.0f, 1.0f, 1.0f), 30000.0f
);
light->getLightData().AmbientColor = video::SColorf(0.5f, 0.5f, 0.5f, 1.0f);
// attach billboard to light
IBillboardSceneNode* bill = smgr->addBillboardSceneNode(
light, core::dimension2d<f32>(30000, 30000)
);
bill->setMaterialFlag(video::EMF_LIGHTING, false);
bill->setMaterialType(video::EMT_TRANSPARENT_ADD_COLOR);
bill->setMaterialTexture(0, driver->getTexture("sprites/particle_white.bmp"));
//-----------------------------------------------------------------------------------------------//
//wasd navigation
//-----------------------------------------------------
SKeyMap keyMap[8];
keyMap[1].Action = EKA_MOVE_FORWARD;
keyMap[1].KeyCode = KEY_KEY_W;
keyMap[3].Action = EKA_MOVE_BACKWARD;
keyMap[3].KeyCode = KEY_KEY_S;
keyMap[5].Action = EKA_STRAFE_LEFT;
keyMap[5].KeyCode = KEY_KEY_A;
keyMap[7].Action = EKA_STRAFE_RIGHT;
keyMap[7].KeyCode = KEY_KEY_D;
// add and setup camera
scene::ICameraSceneNode* camera = 0;
camera = smgr->addCameraSceneNodeFPS(0,80.0f,300.0f,-1, keyMap, 8);
camera->setFarValue (50000.0f) ;
camera->setFOV(1.1f);
camera->setPosition(core::vector3df(1000,1000,0));
camera->setTarget( core::vector3df(0,0,0));
camera->setRotation(core::vector3df(0,0,0));
//-----------------------------------------------------
// some features
//-----------------------------------------------------
device->getCursorControl()->setVisible(false);
smgr->setShadowColor(video::SColor(150,0,0,0));
//-----------------------------------------------------
// starting main render loop
//-----------------------------------------------------
f32 text_rot=0;
int lastFPS = -1;
while(device->run())
{
driver->beginScene(true, true, video::SColor(255,0,0,0));
smgr->drawAll();
driver->endScene();
int fps = driver->getFPS();
if (lastFPS != fps)
{
wchar_t tmp[1024];
swprintf(tmp, 1024, L"MY3D Mesh Loader Example 2 - Irrlicht Engine v.0.10.0 (fps:%d) Triangles:%d",
fps, driver->getPrimitiveCountDrawn());
device->setWindowCaption(tmp);
lastFPS = fps;
}
}
//-----------------------------------------------------
// kill device
//-----------------------------------------------------
device->drop();
return 0;
}
1) you must compress data directory into my3ddata.zip file (my3d scene stilll places in 'data/' dir, but in archieve)
2) add zip file archive with using full files path
Code: Select all
fs->addZipFileArchive("my3ddata.zip", true, false);
Code: Select all
smgr->getParameters()->setParameter(scene::MY3D_TEXTURE_PATH, "");
5) all lightmaps must be in 'Lightmaps/' directory in the same dir as *.my3d file
6) load my3d scenes or textures with full file path
Code: Select all
mesh = smgr->getMesh("data/temple01.my3d");
...
driver->getTexture("data/rocky_up.jpg")
[/i]
I test it with Irrlicht 0.12.0 an everything was just fine.
Check this more carefully.
Good luck.
Well. I'm afraid to say, in my case it STILL doesn't work.
After cutting out the excess stuff in your code posted above it left just a few items relating to the actual my3d loading. On studying them the only thing I found different was you were adding an OCTTREE scenenode from your mesh whereas I just add an AnimatedMesh (tried both loading it as an Ianimatedmesh first and straight as an animatedmeshscenenode).
I have tried many combinations (probably all) of placement of textures/lightmaps/embedded/seperate etc and it will just not work.
IF I put the .m3d + ALL the textures it uses and the LIGHTMAPS folder in the same directory in the archive eg "data/" then the mesh itself is said to have a problem (MAT_HEADER thing) and that it appears to not be a valid format.
IF however I put everything into the root of the archive (ie no real path / ), so that the my3d file and it's textures are sitting directly in the archives root then I get somwhere because it DOES LOAD the mesh and even displays the mesh but it is grey / black as the debug spew shows "COULD NOT FIND TEXTURE/LIGHTMAP" for all the textures used.
If it is of any use I am using 3dsmax7 with your exporter. And have tried embedded and seperate but nothing works. Have you anything more specific to advise?
Basically how you have said to do it, is how I do it and is just the same as if you were not loading it from an archive (same as all other irrlicht stuff) only in my3d case it just doesn't work.
I am going to re-download your examples etc and try it with a noncustom irrlicht build to see if something has messed up in my many tweakings of the irrlicht .dll (but I doubt it).
cheers
After cutting out the excess stuff in your code posted above it left just a few items relating to the actual my3d loading. On studying them the only thing I found different was you were adding an OCTTREE scenenode from your mesh whereas I just add an AnimatedMesh (tried both loading it as an Ianimatedmesh first and straight as an animatedmeshscenenode).
I have tried many combinations (probably all) of placement of textures/lightmaps/embedded/seperate etc and it will just not work.
IF I put the .m3d + ALL the textures it uses and the LIGHTMAPS folder in the same directory in the archive eg "data/" then the mesh itself is said to have a problem (MAT_HEADER thing) and that it appears to not be a valid format.
IF however I put everything into the root of the archive (ie no real path / ), so that the my3d file and it's textures are sitting directly in the archives root then I get somwhere because it DOES LOAD the mesh and even displays the mesh but it is grey / black as the debug spew shows "COULD NOT FIND TEXTURE/LIGHTMAP" for all the textures used.
If it is of any use I am using 3dsmax7 with your exporter. And have tried embedded and seperate but nothing works. Have you anything more specific to advise?
Basically how you have said to do it, is how I do it and is just the same as if you were not loading it from an archive (same as all other irrlicht stuff) only in my3d case it just doesn't work.
I am going to re-download your examples etc and try it with a noncustom irrlicht build to see if something has messed up in my many tweakings of the irrlicht .dll (but I doubt it).
cheers
"If everything will be fine (in uncompressed case) and this error appearing only when you loading from zip archieve i'll try to find out whats wrong..."
Exactly. It loads perfectly when NOT in an archive. It is not corrupt, and I have tried this with many many different my3d files which ALL load perfectly when not in an archive. Believe me I have tried everything logical and normally find my own fixes for problems (added loads of stuff to irrlicht source for my custom dll and have no problems digging into the code having previously written my own - not as good as irrlicht - engine), so it is not anything obviously dumb I am doing, I am doing everything correctly and it still refuses to load right (or at all).
As for "uncompressed" - I have tried embedded and seperate lightmaps - the embedded ones I have tried with no compression. If you mean the archive "uncompressed" I ALWAYS use uncompressed archives as they compress better in the final .exe archive/compression (for online dist) plus irrlicht works that way anyway.
I hope you can look at and fix this soon as I really need to get it working.
Thanks a lot!
Exactly. It loads perfectly when NOT in an archive. It is not corrupt, and I have tried this with many many different my3d files which ALL load perfectly when not in an archive. Believe me I have tried everything logical and normally find my own fixes for problems (added loads of stuff to irrlicht source for my custom dll and have no problems digging into the code having previously written my own - not as good as irrlicht - engine), so it is not anything obviously dumb I am doing, I am doing everything correctly and it still refuses to load right (or at all).
As for "uncompressed" - I have tried embedded and seperate lightmaps - the embedded ones I have tried with no compression. If you mean the archive "uncompressed" I ALWAYS use uncompressed archives as they compress better in the final .exe archive/compression (for online dist) plus irrlicht works that way anyway.
I hope you can look at and fix this soon as I really need to get it working.
Thanks a lot!
OK! Lets starts!!!
I need you my3d scene to play with it.
You can send it to my email zdimitor@pochta.ru
I need you my3d scene to play with it.
You can send it to my email zdimitor@pochta.ru
My (numerous) my3d scenes are the same as the next one. The other poster up above also couldn't load them (And I assume from the lack of replies and NO confirmed loads of them except for yours?) that no-one can load their standard my3d files from an archive.
the file is a collection of meshes in max7 each mesh has only the one material assigned to it (as advised) though I do attache parts of meshes to other parts that use the same material to make use of less lightmaps being generated.
I could try it with a box and a lightmap and see if that works and get back to you, but I can't give assets out unfortunatley as this is for a commercial game due for release at some stage and not a "tech demo".
cheers
the file is a collection of meshes in max7 each mesh has only the one material assigned to it (as advised) though I do attache parts of meshes to other parts that use the same material to make use of less lightmaps being generated.
I could try it with a box and a lightmap and see if that works and get back to you, but I can't give assets out unfortunatley as this is for a commercial game due for release at some stage and not a "tech demo".
cheers