Example #1
0
void Costume::load(string dirPath)
{
	Log::write(LOG_INFO, "Costume\n");
	Log::indent();

	XMLFile xmlFile;
	xmlFile.open(dirPath + XML_FILE_NAME);
	XMLNode *rootNode = xmlFile.getRootNode();

	_name = rootNode->getChild("name")->getStringContent();
	Log::write(LOG_INFO, "name: %s\n", _name.c_str());

	_mirror = rootNode->getChild("mirror")->getBooleanContent();
	Log::write(LOG_INFO, "mirror: %d\n", _mirror);

	int i = 0;
	XMLNode *child;
	while ((child = rootNode->getChild("anim", i++)) != NULL)
	{
		Anim *anim = new Anim();
		anim->load(child);
		_anims.push_back(anim);
	}

	i = 0;
	while ((child = rootNode->getChild("frame", i++)) != NULL)
	{
		Frame *frame = new Frame();
		frame->load(child, dirPath);
		_frames.push_back(frame);
	}

	_paletteData = new PaletteData();
	_paletteData->load(dirPath);

	Log::unIndent();
}
Example #2
0
void Object::load(string dirPath)
{
	Log::write(LOG_INFO, "Object\n");
	Log::indent();

	XMLFile xmlFile;
	xmlFile.open(dirPath + XML_FILE_NAME);
	XMLNode *rootNode = xmlFile.getRootNode();

	_name = rootNode->getChild("name")->getStringContent();
	Log::write(LOG_INFO, "name: %s\n", _name.c_str());

	_displayName = rootNode->getChild("displayName")->getStringContent();
	Log::write(LOG_INFO, "displayName: %s\n", _displayName.c_str());

	_hotspotX = rootNode->getChild("hotspotX")->getIntegerContent();
	Log::write(LOG_INFO, "hotspotX: %u\n", _hotspotX);

	_hotspotY = rootNode->getChild("hotspotY")->getIntegerContent();
	Log::write(LOG_INFO, "hotspotY: %u\n", _hotspotY);

	_x = rootNode->getChild("x")->getIntegerContent();
	Log::write(LOG_INFO, "x: %u\n", _x);

	_y = rootNode->getChild("y")->getIntegerContent();
	Log::write(LOG_INFO, "y: %u\n", _y);

	_width = rootNode->getChild("width")->getIntegerContent();
	Log::write(LOG_INFO, "width: %u\n", _width);

	_height = rootNode->getChild("height")->getIntegerContent();
	Log::write(LOG_INFO, "height: %u\n", _height);

	string actorDir = rootNode->getChild("actorDir")->getStringContent();
	if (actorDir == "west")
		_actorDir = ACTOR_DIR_WEST;
	else if (actorDir == "east")
		_actorDir = ACTOR_DIR_EAST;
	else if (actorDir == "south")
		_actorDir = ACTOR_DIR_SOUTH;
	else if (actorDir == "north")
		_actorDir = ACTOR_DIR_NORTH;
	else
		Log::write(LOG_ERROR, "Unable to convert actorDir \"%s\" !\n", actorDir.c_str());
	Log::write(LOG_INFO, "actorDir: %s (%u)\n", actorDir.c_str(), _actorDir);

	int i = 0;
	XMLNode *child;
	while ((child = rootNode->getChild("image", i++)) != NULL)
	{
		Image *image = new Image();
		image->load(dirPath + child->getStringContent() + "/");
		_images.push_back(image);
	}

	if (!_images.empty())
	{
		_paletteData = new PaletteData();
		_paletteData->load(dirPath);
	}

	// Change hotspots from absolute to relative positions
	_hotspotX -= _x;
	_hotspotY -= _y;

	Log::unIndent();
}
Example #3
0
bool assemblekeybif(char *fname, uint8 **mem, uint32 *size)
{
	int pr;
	std::string bfname, rfname, resref;
	std::vector<uint8 *> datas;
	uint16 drives=0;
	uint32 asize;
	uint64 tmp;
	NWNFileType restype=NWN_FILE_UNDEFINED;
	bool newbif=true, withCd=false, exploded=false;
	XMLFile xml;
	KEYFile key;
	BIFFile bif;

	if(xml.open(fname))
	{
		std::cerr << "Error opening file \"" << fname << "\": ";
		std::cerr << xml.getStrError() << "\n";
		return false;
	}
	while((pr = xml.parse()) >= 0)
	{
		switch(pr)
		{
			case 0:
				if(!mem && (xml.section == ".key.filename"))
					key.filename = xml.value;
				else if(xml.section == ".key.filetype")
				{
					if((key.type = key.getFileResTypeByExt(xml.value)) == -1)
						return printxmlerr(xml, "Unknown filetype");
					if(!key.typeIsCorrect()) return printxmlerr(xml, "No KEY type");
				}
				else if(xml.section == ".key.buildyear")
				{
					sscanf(xml.value.c_str(), S_UINT64, &tmp);
					key.buildyear = (uint32) (tmp - 1900);
				}
				else if(xml.section == ".key.buildday")
				{
					sscanf(xml.value.c_str(), S_UINT64, &tmp);
					key.buildday = (uint32) tmp;
				}
				else if(xml.section == ".key.bif.filename")
					bfname = xml.value;
				else if(xml.section == ".key.bif.drives")
				{
					sscanf(xml.value.c_str(), S_UINT64, &tmp);
					drives = (uint16) tmp;
				}
				else if(xml.section == ".key.bif.variable.resource.resref")
					resref = xml.value;
				else if(xml.section == ".key.bif.variable.resource.filename")
					rfname = xml.value;
				else if(xml.section == ".key.bif.variable.resource.restype")
				{
					if((restype = key.getFileResTypeByExt(xml.value)) == -1)
						return printxmlerr(xml, "Unknown filetype");
				}
				else if(xml.section == ".key.bif.variable.resource.withCd")
				{
					sscanf(xml.value.c_str(), S_UINT64, &tmp);
					withCd = (bool) tmp;
				}
				else if(xml.section == ".key.bif.variable.resource.exploded")
				{
					sscanf(xml.value.c_str(), S_UINT64, &tmp);
					exploded = (bool) tmp;
				}
				break;
			case 1:
				if(xml.section == ".bif.fixed")
					return printxmlerr(xml, "Fixed resources aren't supported");
				else if((xml.section != ".?xml") && (xml.section != ".key") &&
				   (getpos(validkeybiftags, KEYBIFTAGS, xml.section) == -1))
					return printxmlerr(xml, "Invalid tag");
				break;
			case 2:
				if(xml.value == ".key.bif")
				{
					bfname = bif.filename;
					if(bif.endwrite()) return printxmlerr(xml, bif.getStrError());
					if(bif.open(bfname)) return printxmlerr(xml, bif.getStrError());
					key.fsizes[key.bifcount-1] = bif.getFileSize();
					bif.deInit();
					newbif = true;
					bfname.clear();
					drives = 0;
				}
				else if(xml.value == ".key.bif.variable.resource")
				{
					if(newbif)
					{
						if(bfname.empty()) return printxmlerr(xml, "Missing filename");
						if(key.addBif(bfname, drives, 0))
							return printxmlerr(xml, key.getStrError());
						if(bif.beginWrite(getbasename((char*)bfname.c_str())))
							return printxmlerr(xml, bif.getStrError());
						bif.type = NWN_FILE_BIF;
						newbif = false;
					}
					if(resref.empty()) return printxmlerr(xml, "Missing resref");
					if(rfname.empty()) return printxmlerr(xml, "Missing filename");
					if(restype == NWN_FILE_UNDEFINED)
						return printxmlerr(xml, "Missing restype");
					if(exploded)
					{
						datas.resize((tmp=datas.size())+1);
						if(!(datas[tmp] = expd(xml, bif.getBaseType(restype), rfname, asize)))
							return false;
						if(bif.writeData(restype, withCd, true, datas[tmp], asize, false))
							return printxmlerr(xml, bif.getStrError());
					}
					else
						if(bif.writeData(restype, withCd, true, rfname))
							return printxmlerr(xml, bif.getStrError());
					if(key.addResource(key.bifcount-1, resref, restype, bif.vrescount-1))
						return printxmlerr(xml, key.getStrError());
					resref.clear();
					rfname.clear();
					restype = NWN_FILE_UNDEFINED;
					withCd = exploded = false;
				}
				break;
		}
	}
	if(pr != -6) return printxmlerr(xml, xml.getStrError());

	xml.close();
	if(!mem)
	{
		if(key.filename.empty()) return printxmlerr(xml, "Missing filename");
		else if(key.write(key.filename)) return printnwnerr(key);
	}
	else if(key.write(mem, size)) return printnwnerr(key);
	for(uint32 i=0;i<datas.size();i++) free(datas[i]);
	return true;
}
Example #4
0
bool assembletlk(char *fname, uint8 **mem, uint32 *size)
{
	int pr;
	uint32 flags=0;
	uint64 tmp;
	float32 sndlength=0;
	std::string sndresref, str;
	XMLFile xml;
	TLKFile tlk;

	if(xml.open(fname))
	{
		std::cerr << "Error opening file \"" << fname << "\": ";
		std::cerr << xml.getStrError() << "\n";
		return false;
	}
	while((pr = xml.parse()) >= 0)
	{
		switch(pr)
		{
			case 0:
				if(!mem && (xml.section == ".tlk.filename"))
					tlk.filename = xml.value;
				else if(xml.section == ".tlk.filetype")
				{
					if((tlk.type = tlk.getFileResTypeByExt(xml.value)) == -1)
						return printxmlerr(xml, "Unknown filetype");
					if(!tlk.typeIsCorrect()) return printxmlerr(xml, "No TLK type");
				}
				else if(xml.section == ".tlk.language")
				{
					if((tlk.language = (NWNLang) getpos(langs, LANGS, xml.value)) == -1)
						return printxmlerr(xml, "Invalid language");
				}
				else if(xml.section == ".tlk.std::string.sndresref")
					sndresref = xml.value;
				else if(xml.section == ".tlk.std::string.flags")
				{
					sscanf(xml.value.c_str(), S_UINT64, &tmp);
					flags = (uint32) tmp;
				}
				else if(xml.section == ".tlk.std::string.sndlength")
					sscanf(xml.value.c_str(), S_FLOAT32, &sndlength);
				else if(xml.section == ".tlk.std::string")
					str = xml.value;
				break;
			case 1:
				if((xml.section != ".?xml") && (xml.section != ".tlk") &&
						(getpos(validtlktags, TLKTAGS, xml.section) == -1))
					return printxmlerr(xml, "Invalid tag");
				break;
			case 2:
				if(xml.value == ".tlk.std::string")
				{
					if(tlk.add(flags, sndresref, sndlength, unquotestr(str)))
						return printxmlerr(xml, tlk.getStrError());
					sndlength = flags = 0;
					str.clear();
					sndresref.clear();
				}
				break;
		}
	}
	if(pr != -6) return printxmlerr(xml, xml.getStrError());

	xml.close();
	if(!mem)
	{
		if(tlk.filename.empty()) return printxmlerr(xml, "Missing filename");
		else if(tlk.write(tlk.filename)) return printnwnerr(tlk);
	}
	else if(tlk.write(mem, size)) return printnwnerr(tlk);
	return true;
}
Example #5
0
bool assemblegff(char *fname, uint8 **mem, uint32 *size)
{
	int pr;
	uint32 n=0;
	XMLFile xml;
	GFFFile gff;

	if(xml.open(fname))
	{
		std::cerr << "Error opening file \"" << fname << "\": ";
		std::cerr << xml.getStrError() << "\n";
		return false;
	}
	while((pr = xml.parse()) >= 0)
	{
		switch(pr)
		{
//		std::cout << pr << ": " << xml.section << " = \"" << xml.value << "\"\n";
			case 0:
				if(!mem && (xml.section == ".gff.filename"))
				{
					if(gff.beginWrite(xml.value))
						return printxmlerr(xml, gff.getStrError());
				}
				else if(xml.section == ".gff.filetype")
				{
					if((gff.type = gff.getFileResTypeByExt(xml.value)) == -1)
						return printxmlerr(xml, "Unknown filetype");
					if(!gff.typeIsCorrect()) return printxmlerr(xml, "No GFF type");
				}
				break;
			case 1:
				if(xml.section == ".gff.struct")
				{
					if(n)
						return printxmlerr(xml, "Must have exactly one top level struct");
					if(!mem)
					{
						if(gff.filename.empty()) return printxmlerr(xml, "Missing filename");
					}
					else
					{
						if(gff.beginWrite())
							return printxmlerr(xml, gff.getStrError());
					}
					if(gff.writeStruct(n, "", 0))
						return printxmlerr(xml, gff.getStrError());
					if(!assemblegffstruct(xml, gff, n++, NULL)) return false;
				}
				else if((xml.section != ".?xml") && (xml.section != ".gff"))
				{
					if(getpos(validgfftags, GFFTAGS, xml.section) == -1)
						return printxmlerr(xml, "Invalid tag");
					else
						return printxmlerr(xml, "Element outside the top level struct");
				}
				break;
		}
	}
	if(pr != -6) return printxmlerr(xml, xml.getStrError());

	xml.close();
	if(gff.endwrite(mem, size)) return printxmlerr(xml, gff.getStrError());
	return true;
}
Example #6
0
bool assemblessf(char *fname, uint8 **mem, uint32 *size)
{
	int pr;
	uint32 stringref=0xFFFFFFFF;
	uint64 tmp;
	std::string resref;
	XMLFile xml;
	SSFFile ssf;

	if(xml.open(fname))
	{
		std::cerr << "Error opening file \"" << fname << "\": ";
		std::cerr << xml.getStrError() << "\n";
		return false;
	}
	while((pr = xml.parse()) >= 0)
	{
		switch(pr)
		{
			case 0:
				if(!mem && (xml.section == ".ssf.filename"))
					ssf.filename = xml.value;
				else if(xml.section == ".ssf.filetype")
				{
					if((ssf.type = ssf.getFileResTypeByExt(xml.value)) == -1)
						return printxmlerr(xml, "Unknown filetype");
					if(!ssf.typeIsCorrect()) return printxmlerr(xml, "No SSF type");
				}
				else if(xml.section == ".ssf.sound.resref")
					resref = xml.value;
				else if(xml.section == ".ssf.sound.stringref")
				{
					sscanf(xml.value.c_str(), S_UINT64, &tmp);
					stringref = (uint32) tmp;
				}
				break;
			case 1:
				if((xml.section != ".?xml") && (xml.section != ".ssf") &&
						(getpos(validssftags, SSFTAGS, xml.section) == -1))
					return printxmlerr(xml, "Invalid tag");
				break;
			case 2:
				if(xml.value == ".ssf.sound")
				{
					if(ssf.add(resref, stringref))
						return printxmlerr(xml, ssf.getStrError());
					resref.clear();
					stringref = 0xFFFFFFFF;
				}
				break;
		}
	}
	if(pr != -6) return printxmlerr(xml, xml.getStrError());

	xml.close();
	if(!mem)
	{
		if(ssf.filename.empty()) return printxmlerr(xml, "Missing filename");
		else if(ssf.write(ssf.filename)) return printnwnerr(ssf);
	}
	else if(ssf.write(mem, size)) return printnwnerr(ssf);
	return true;
}
Example #7
0
bool assemblebif(char *fname, uint8 **mem, uint32 *size)
{
	int pr;
	uint32 asize;
	uint64 tmp;
	std::vector<uint8 *> datas;
	std::string filename;
	bool opened=false, exploded=false, withCd=false;
	NWNFileType restype=NWN_FILE_UNDEFINED;
	XMLFile xml;
	BIFFile bif;

	if(xml.open(fname))
	{
		std::cerr << "Error opening file \"" << fname << "\": ";
		std::cerr << xml.getStrError() << "\n";
		return false;
	}
	while((pr = xml.parse()) >= 0)
	{
		switch(pr)
		{
			case 0:
				if(!mem && (xml.section == ".bif.filename"))
				{
					if(bif.beginWrite(xml.value))
						return printxmlerr(xml, bif.getStrError());
				}
				else if(xml.section == ".bif.filetype")
				{
					if((bif.type = bif.getFileResTypeByExt(xml.value)) == -1)
						return printxmlerr(xml, "Unknown filetype");
					if(!bif.typeIsCorrect()) return printxmlerr(xml, "No BIF type");
				}
				else if(xml.section == ".bif.variable.resource.filename")
					filename = xml.value;
				else if(xml.section == ".bif.variable.resource.restype")
				{
					if((restype = bif.getFileResTypeByExt(xml.value)) == -1)
						return printxmlerr(xml, "Unknown filetype");
				}
				else if(xml.section == ".bif.variable.resource.exploded")
				{
					sscanf(xml.value.c_str(), S_UINT64, &tmp);
					exploded = (bool) tmp;
				}
				else if(xml.section == ".bif.variable.resource.withCd")
				{
					sscanf(xml.value.c_str(), S_UINT64, &tmp);
					withCd = (bool) tmp;
				}
				break;
			case 1:
				if(xml.section == ".bif.fixed")
					return printxmlerr(xml, "Fixed resources aren't supported");
				else if((xml.section != ".?xml") && (xml.section != ".bif") &&
				        (getpos(validbiftags, BIFTAGS, xml.section) == -1))
					return printxmlerr(xml, "Invalid tag");
				break;
			case 2:
				if(xml.value == ".bif.variable.resource")
				{
					if(!opened)
					{
						if(!mem)
						{
							if(bif.filename.empty())
								return printxmlerr(xml, "Missing filename");
						}
						else
							if(bif.beginWrite()) return printxmlerr(xml, bif.getStrError());
						opened = true;
					}
					if(filename.empty()) return printxmlerr(xml, "Missing filename");
					if(restype == NWN_FILE_UNDEFINED)
						return printxmlerr(xml, "Missing restype");
					if(exploded)
					{
						datas.resize((tmp=datas.size())+1);
						if(!(datas[tmp] = expd(xml, bif.getBaseType(restype), filename, asize)))
							return false;
						if(bif.writeData(restype, withCd, true, datas[tmp], asize, false))
							return printxmlerr(xml, bif.getStrError());
					}
					else
						if(bif.writeData(restype, withCd, true, filename))
							return printxmlerr(xml, bif.getStrError());
					filename.clear();
					exploded = withCd = false;
					restype=NWN_FILE_UNDEFINED;
				}
				break;
		}
	}
	if(pr != -6) return printxmlerr(xml, xml.getStrError());

	xml.close();
	if(bif.endwrite(mem, size)) return printxmlerr(xml, bif.getStrError());
	for(uint32 i=0;i<datas.size();i++) free(datas[i]);
	return true;
}
Example #8
0
bool assemblekey(char *fname, uint8 **mem, uint32 *size)
{
	int pr;
	std::string filename, resref;
	uint16 drives=0;
	uint32 filesize=0, index=0xFFFFFFFF;
	uint64 tmp;
	NWNFileType restype=NWN_FILE_UNDEFINED;
	bool newbif=true;
	XMLFile xml;
	KEYFile key;

	if(xml.open(fname))
	{
		std::cerr << "Error opening file \"" << fname << "\": ";
		std::cerr << xml.getStrError() << "\n";
		return false;
	}
	while((pr = xml.parse()) >= 0)
	{
		switch(pr)
		{
			case 0:
				if(!mem && (xml.section == ".key.filename"))
					key.filename = xml.value;
				else if(xml.section == ".key.filetype")
				{
					if((key.type = key.getFileResTypeByExt(xml.value)) == -1)
						return printxmlerr(xml, "Unknown filetype");
					if(!key.typeIsCorrect()) return printxmlerr(xml, "No KEY type");
				}
				else if(xml.section == ".key.buildyear")
				{
					sscanf(xml.value.c_str(), S_UINT64, &tmp);
					key.buildyear = (uint32) (tmp - 1900);
				}
				else if(xml.section == ".key.buildday")
				{
					sscanf(xml.value.c_str(), S_UINT64, &tmp);
					key.buildday = (uint32) tmp;
				}
				else if(xml.section == ".key.bif.filename")
					filename = xml.value;
				else if(xml.section == ".key.bif.filesize")
				{
					sscanf(xml.value.c_str(), S_UINT64, &tmp);
					filesize = (uint32) tmp;
				}
				else if(xml.section == ".key.bif.drives")
				{
					sscanf(xml.value.c_str(), S_UINT64, &tmp);
					drives = (uint16) tmp;
				}
				else if(xml.section == ".key.bif.resource.resref")
					resref = xml.value;
				else if(xml.section == ".key.bif.resource.index")
				{
					sscanf(xml.value.c_str(), S_UINT64, &tmp);
					index = (uint32) tmp;
				}
				else if(xml.section == ".key.bif.resource.restype")
				{
					if((restype = key.getFileResTypeByExt(xml.value)) == -1)
						return printxmlerr(xml, "Unknown filetype");
				}
				break;
			case 1:
				if((xml.section != ".?xml") && (xml.section != ".key") &&
				   (getpos(validkeytags, KEYTAGS, xml.section) == -1))
					return printxmlerr(xml, "Invalid tag");
				break;
			case 2:
				if(xml.value == ".key.bif")
				{
					newbif = true;
					filesize = drives = 0;
					filename.clear();
				}
				else if(xml.value == ".key.bif.resource")
				{
					if(newbif)
					{
						if(filename.empty()) return printxmlerr(xml, "Missing filename");
						if(key.addBif(filename, drives, filesize))
						return printxmlerr(xml, key.getStrError());
						newbif = false;
					}
					if(resref.empty()) return printxmlerr(xml, "Missing resref");
					if(restype == NWN_FILE_UNDEFINED)
						return printxmlerr(xml, "Missing restype");
					if(index == 0xFFFFFFFF) printxmlerr(xml, "Missing index");
					if(key.addResource(key.bifcount-1, resref, restype, index))
						return printxmlerr(xml, key.getStrError());
					resref.clear();
					restype = NWN_FILE_UNDEFINED;
					index = 0xFFFFFFFF;
				}
				break;
		}
	}
	if(pr != -6) return printxmlerr(xml, xml.getStrError());

	xml.close();
	if(!mem)
	{
		if(key.filename.empty()) return printxmlerr(xml, "Missing filename");
		else if(key.write(key.filename)) return printnwnerr(key);
	}
	else if(key.write(mem, size)) return printnwnerr(key);
	return true;
}
Example #9
0
bool assembleerf(char *fname, uint8 **mem, uint32 *size)
{
	int pr;
	uint32 asize;
	uint64 tmp;
	std::vector<uint8 *> datas;
	bool opened=false, exploded=false;
	std::string resref, filename;
	NWNFileType restype=NWN_FILE_UNDEFINED;
	XMLFile xml;
	ERFFile erf;

	if(xml.open(fname))
	{
		std::cerr << "Error opening file \"" << fname << "\": ";
		std::cerr << xml.getStrError() << "\n";
		return false;
	}
	while((pr = xml.parse()) >= 0)
	{
		switch(pr)
		{
			case 0:
				if(!mem && (xml.section == ".erf.filename"))
				{
					if(erf.beginWrite(xml.value))
						return printxmlerr(xml, erf.getStrError());
				}
				else if(xml.section == ".erf.filetype")
				{
					if((erf.type = erf.getFileResTypeByExt(xml.value)) == -1)
						return printxmlerr(xml, "Unknown filetype");
					if(!erf.typeIsCorrect()) return printxmlerr(xml, "No ERF type");
				}
				else if(xml.section == ".erf.buildyear")
				{
					sscanf(xml.value.c_str(), S_UINT64, &tmp);
					erf.buildyear = (uint32) (tmp - 1900);
				}
				else if(xml.section == ".erf.buildday")
				{
					sscanf(xml.value.c_str(), S_UINT64, &tmp);
					erf.buildday = (uint32) tmp;
				}
				else if(xml.section == ".erf.resource.resref")
					resref = xml.value;
				else if(xml.section == ".erf.resource.filename")
					filename = xml.value;
				else if(xml.section == ".erf.resource.restype")
				{
					if((restype = erf.getFileResTypeByExt(xml.value)) == -1)
						return printxmlerr(xml, "Unknown filetype");
				}
				else if(xml.section == ".erf.resource.exploded")
				{
					sscanf(xml.value.c_str(), S_UINT64, &tmp);
					exploded = (bool) tmp;
				}
				break;
			case 1:
				if(xml.section == ".erf.description") {
					if(!assembleerfdesc(xml, erf)) return false;
				} else if((xml.section != ".?xml") && (xml.section != ".erf") &&
				        (getpos(validerftags, ERFTAGS, xml.section) == -1))
					return printxmlerr(xml, "Invalid tag");
				break;
			case 2:
				if(xml.value == ".erf.resource")
				{
					if(!opened)
					{
						if(!mem)
						{
							if(erf.filename.empty())
								return printxmlerr(xml, "Missing filename");
						}
						else
							if(erf.beginWrite()) return printxmlerr(xml, erf.getStrError());
						opened = true;
					}
					if(resref.empty()) return printxmlerr(xml, "Missing resref");
					if(filename.empty()) return printxmlerr(xml, "Missing filename");
					if(restype == NWN_FILE_UNDEFINED)
						return printxmlerr(xml, "Missing restype");
					if(exploded)
					{
						datas.resize((tmp=datas.size())+1);
						if(!(datas[tmp] = expd(xml, erf.getBaseType(restype), filename, asize)))
							return false;
						if(erf.writeData(resref, restype, datas[tmp], asize, false))
							return printxmlerr(xml, erf.getStrError());
					}
					else
						if(erf.writeData(resref, restype, filename))
							return printxmlerr(xml, erf.getStrError());
					resref.clear();
					filename.clear();
					exploded = false;
					restype=NWN_FILE_UNDEFINED;
				}
				break;
		}
	}
	if(pr != -6) return printxmlerr(xml, xml.getStrError());

	xml.close();
	if(erf.endwrite(mem, size)) return printxmlerr(xml, erf.getStrError());
	for(uint32 i=0;i<datas.size();i++) free(datas[i]);
	return true;
}