Loading MY3D files from a ZIP ARCHIVE

You discovered a bug in the engine, and you are sure that it is not a problem of your code? Just post it in here. Please read the bug posting guidelines first.
GX

Loading MY3D files from a ZIP ARCHIVE

Post by GX »

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
afecelis
Admin
Posts: 3075
Joined: Sun Feb 22, 2004 10:44 pm
Location: Colombia
Contact:

Post by afecelis »

the problem is not in the My3d file itself but in the set texture path parameter:

Code: Select all

smgr->getParameters()->setParameter(scene::MY3D_TEXTURE_PATH, "./data/"); 
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.
GX

Post by GX »

Thanks for the info.
So Niko/Zdiminator can we expect a fix for this at some stage? (i.e are you aware of it and intending to fix it?) if not please say so I can look at other formats. I can't really have a central asset storage file with stray elements left outside.. not nice ;)


cheers
Guest

Post by Guest »

bump ^^

Any news on whether this "bug" is officially recognized and/or being worked on.. even a hint on where to fix it would be good and I'll try to fix it myself (ie from Niko/Zdiminator)

thanks
jx

Post by jx »

I'd like to know.
niko
Site Admin
Posts: 1759
Joined: Fri Aug 22, 2003 4:44 am
Location: Vienna, Austria
Contact:

Post by niko »

I've put the bug on my list. In the meantime, maybe you just could live without zip files. Or I should make it possible to add custom archives to the engine.
Guest

Post by Guest »

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!
ZDimitor
Posts: 202
Joined: Fri Jul 16, 2004 3:27 am
Location: Russia

Post by ZDimitor »

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.

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;  
}

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

Code: Select all

fs->addZipFileArchive("my3ddata.zip", true, false); 
3) we dont need this string parameter

Code: Select all

smgr->getParameters()->setParameter(scene::MY3D_TEXTURE_PATH, ""); 
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

Code: Select all

mesh = smgr->getMesh("data/temple01.my3d");
...
driver->getTexture("data/rocky_up.jpg")
Thats all.
[/i]


I test it with Irrlicht 0.12.0 an everything was just fine.

Check this more carefully.

Good luck.
Guest

Post by Guest »

WOW! Thanks Z. Can't believe I have actually got this code after waiting so long. I apreciate it greatly. And thanks to Niko for saying he would look at it also (hopefully using your code above)

thanks again! :)
Guest

Post by Guest »

ok just realised, as you say - not really any changes to the source needed just the way we do it.

thnx
Guest

Post by Guest »

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
ZDimitor
Posts: 202
Joined: Fri Jul 16, 2004 3:27 am
Location: Russia

Post by ZDimitor »

Weel if you have any messages about MAT_HEADER it mean your my3d file is corrupted.
Try to load it uncompressed.
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...
Guest

Post by Guest »

"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! :)
ZDimitor
Posts: 202
Joined: Fri Jul 16, 2004 3:27 am
Location: Russia

Post by ZDimitor »

OK! Lets starts!!!

I need you my3d scene to play with it.

You can send it to my email zdimitor@pochta.ru
Guest

Post by Guest »

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
Post Reply