Ejemplo n.º 1
0
void cloneSelected(const cmd::ArgumentList& args)
{
	// Check for the correct editing mode (don't clone components)
	if (GlobalSelectionSystem().Mode() == SelectionSystem::eComponent) {
		return;
	}

	UndoableCommand undo("cloneSelected");

	// Create the list that will take the cloned instances
	SelectionCloner::Map cloned;

	SelectionCloner cloner;
	GlobalSceneGraph().root()->traverse(cloner);

	// Create a new namespace and move all cloned nodes into it
	INamespacePtr clonedNamespace = GlobalNamespaceFactory().createNamespace();
	assert(clonedNamespace != NULL);

	// Move items into the temporary namespace, this will setup the links
	clonedNamespace->connect(cloner.getCloneRoot());

	// Get the namespace of the current map
	scene::IMapRootNodePtr mapRoot = GlobalMapModule().getRoot();
	if (mapRoot == NULL) return; // not map root (this can happen)

	INamespacePtr nspace = mapRoot->getNamespace();
	if (nspace)
    {
		// Prepare the nodes for import
		nspace->ensureNoConflicts(cloner.getCloneRoot());
		// Now move all nodes into the target namespace
		nspace->connect(cloner.getCloneRoot());
	}

	// Unselect the current selection
	GlobalSelectionSystem().setSelectedAll(false);

	// Finally, move the cloned nodes to their destination and select them
	cloner.moveClonedNodes(true);

	if (registry::getValue<int>(RKEY_OFFSET_CLONED_OBJECTS) == 1)
	{
		// Move the current selection by one grid unit to the "right" and "downwards"
		nudgeSelected(eNudgeDown);
		nudgeSelected(eNudgeRight);
	}
}
Ejemplo n.º 2
0
void AseExporter::exportToStream(std::ostream& stream)
{
	// Header / scene block
	stream << "*3DSMAX_ASCIIEXPORT	200" << std::endl;
	stream << "*COMMENT \"DarkRadiant ASCII Scene Export(*.ase)\"" << std::endl;
	stream << "*SCENE {" << std::endl;
	stream << "\t*SCENE_FILENAME \"" << GlobalMapModule().getMapName() << "\"" << std::endl;
	stream << "\t*SCENE_FIRSTFRAME 0" << std::endl;
	stream << "\t*SCENE_LASTFRAME 100" << std::endl;
	stream << "\t*SCENE_FRAMESPEED 30" << std::endl;
	stream << "\t*SCENE_TICKSPERFRAME 160" << std::endl;
	stream << "\t*SCENE_BACKGROUND_STATIC 0.0000	0.0000	0.0000" << std::endl;
	stream << "\t*SCENE_AMBIENT_STATIC 0.0000	0.0000	0.0000" << std::endl;
	stream << "}" << std::endl;

	// Materials
	stream << "*MATERIAL_LIST {" << std::endl;
	stream << "\t*MATERIAL_COUNT " << _surfaces.size() << std::endl;

	std::size_t m = 0;

	for (const Surfaces::value_type& pair : _surfaces)
	{
		std::string aseMaterial = pair.second.materialName;
		string::replace_all(aseMaterial, "/", "\\");

		stream << "\t*MATERIAL " << m << " {" << std::endl;
		stream << "\t\t*MATERIAL_NAME \"" << aseMaterial << "\"" << std::endl;
		stream << "\t\t*MATERIAL_CLASS \"Standard\"" << std::endl;
		stream << "\t\t*MATERIAL_AMBIENT 0.5882	0.5882	0.5882" << std::endl;
		stream << "\t\t*MATERIAL_DIFFUSE 0.5882	0.5882	0.5882" << std::endl;
		stream << "\t\t*MATERIAL_SPECULAR 0.9000	0.9000	0.9000" << std::endl;
		stream << "\t\t*MATERIAL_SHINE 0.1000" << std::endl;
		stream << "\t\t*MATERIAL_SHINESTRENGTH 0.0000" << std::endl;
		stream << "\t\t*MATERIAL_TRANSPARENCY 0.0000" << std::endl;
		stream << "\t\t*MATERIAL_WIRESIZE 1.0000" << std::endl;
		stream << "\t\t*MATERIAL_SHADING Blinn" << std::endl;
		stream << "\t\t*MATERIAL_XP_FALLOFF 0.0000" << std::endl;
		stream << "\t\t*MATERIAL_SELFILLUM 0.0000" << std::endl;
		stream << "\t\t*MATERIAL_FALLOFF In" << std::endl;
		stream << "\t\t*MATERIAL_XP_TYPE Filter" << std::endl;
		stream << "\t\t*MAP_DIFFUSE {" << std::endl;
		stream << "\t\t\t*MAP_NAME \"" << aseMaterial << "\"" << std::endl;
		stream << "\t\t\t*MAP_CLASS \"Bitmap\"" << std::endl;
		stream << "\t\t\t*MAP_SUBNO 1" << std::endl;
		stream << "\t\t\t*MAP_AMOUNT 1.0000" << std::endl;
		stream << "\t\t\t*BITMAP \"\\\\purgatory\\purgatory\\doom\\base\\" << aseMaterial << "\"" << std::endl;
		stream << "\t\t\t*MAP_TYPE Screen" << std::endl;
		stream << "\t\t\t*UVW_U_OFFSET 0.0000" << std::endl;
		stream << "\t\t\t*UVW_V_OFFSET 0.0000" << std::endl;
		stream << "\t\t\t*UVW_U_TILING 1.0000" << std::endl;
		stream << "\t\t\t*UVW_V_TILING 1.0000" << std::endl;
		stream << "\t\t\t*UVW_ANGLE 0.0000" << std::endl;
		stream << "\t\t\t*UVW_BLUR 1.0000" << std::endl;
		stream << "\t\t\t*UVW_BLUR_OFFSET 0.0000" << std::endl;
		stream << "\t\t\t*UVW_NOUSE_AMT 1.0000" << std::endl;
		stream << "\t\t\t*UVW_NOISE_SIZE 1.0000" << std::endl;
		stream << "\t\t\t*UVW_NOISE_LEVEL 1" << std::endl;
		stream << "\t\t\t*UVW_NOISE_PHASE 0.0000" << std::endl;
		stream << "\t\t\t*BITMAP_FILTER Pyramidal" << std::endl;
		stream << "\t\t}" << std::endl;
		stream << "\t}" << std::endl;

		++m;
	}

	stream << "}" << std::endl; // Material List End

	// Geom Objects
	m = 0;

	for (const Surfaces::value_type& pair : _surfaces)
	{
		const Surface& surface = pair.second;

		stream << "*GEOMOBJECT {" << std::endl;

		stream << "\t*NODE_NAME \"mesh" << m << "\"" << std::endl;
		stream << "\t*NODE_TM {" << std::endl;
		stream << "\t\t*NODE_NAME \"mesh" << m << "\"" << std::endl;
		stream << "\t\t*INHERIT_POS 0 0 0" << std::endl;
		stream << "\t\t*INHERIT_ROT 0 0 0" << std::endl;
		stream << "\t\t*INHERIT_SCL 0 0 0" << std::endl;
		stream << "\t\t*TM_ROW0 1.0000	0.0000	0.0000" << std::endl;
		stream << "\t\t*TM_ROW1 0.0000	1.0000	0.0000" << std::endl;
		stream << "\t\t*TM_ROW2 0.0000	0.0000	1.0000" << std::endl;
		stream << "\t\t*TM_ROW3 0.0000	0.0000	0.0000" << std::endl;
		stream << "\t\t*TM_POS 0.0000	0.0000	0.0000" << std::endl;
		stream << "\t\t*TM_ROTAXIS 0.0000	0.0000	0.0000" << std::endl;
		stream << "\t\t*TM_ROTANGLE 0.0000" << std::endl;
		stream << "\t\t*TM_SCALE 1.0000	1.0000	1.0000" << std::endl;
		stream << "\t\t*TM_SCALEAXIS 0.0000	0.0000	0.0000" << std::endl;
		stream << "\t\t*TM_SCALEAXISANG 0.0000" << std::endl;
		stream << "\t}" << std::endl;

		stream << "\t*MESH {" << std::endl;

		stream << "\t\t*TIMEVALUE 0" << std::endl;
		stream << "\t\t*MESH_NUMVERTEX " << surface.vertices.size() << std::endl;
		stream << "\t\t*MESH_NUMFACES " << (surface.indices.size() / 3) << std::endl;

		// Vertices
		stream << "\t\t*MESH_VERTEX_LIST {" << std::endl;

		for (std::size_t v = 0; v < surface.vertices.size(); ++v)
		{
			const Vertex3f& vert = surface.vertices[v].vertex;

			stream << "\t\t\t*MESH_VERTEX " << v << "\t" << vert.x() << "\t" << vert.y() << "\t" << vert.z() << std::endl;
		}

		stream << "\t\t}" << std::endl;

		// Faces
		stream << "\t\t*MESH_FACE_LIST {" << std::endl;

		for (std::size_t i = 0; i+2 < surface.indices.size(); i += 3)
		{
			std::size_t faceNum = i / 3;

			stream << fmt::format("\t\t\t*MESH_FACE {:3d}:  A: {:3d} B: {:3d} C: {:3d} AB:       0 BC:    0 CA:    0	 *MESH_SMOOTHING 1 	*MESH_MTLID {:3d}",
				faceNum, surface.indices[i], surface.indices[i + 1], surface.indices[i + 2], m) << std::endl;
		}

		stream << "\t\t}" << std::endl;

		stream << "\t\t*MESH_NUMTVERTEX " << surface.vertices.size() << std::endl;

		stream << "\t\t*MESH_TVERTLIST {" << std::endl;

		for (std::size_t v = 0; v < surface.vertices.size(); ++v)
		{
			const TexCoord2f& tex = surface.vertices[v].texcoord;
			
			// Invert the T coordinate
			stream << "\t\t\t*MESH_TVERT " << v << "\t" << tex.x() << "\t" << (-tex.y()) << "\t0.0000" << std::endl;
		}

		stream << "\t\t}" << std::endl;
		
		// TFaces
		stream << "\t\t*MESH_NUMTVFACES " << (surface.indices.size() / 3) << std::endl;
		stream << "\t\t*MESH_TFACELIST {" << std::endl;

		for (std::size_t i = 0; i + 2 < surface.indices.size(); i += 3)
		{
			std::size_t faceNum = i / 3;

			stream << fmt::format("\t\t\t*MESH_TFACE {:3d}\t{:3d}\t{:3d}\t{:3d}",
				faceNum, surface.indices[i], surface.indices[i + 1], surface.indices[i + 2]) << std::endl;
		}

		stream << "\t\t}" << std::endl;

		// CVerts
		stream << "\t\t*MESH_NUMCVERTEX " << surface.vertices.size() << std::endl;

		stream << "\t\t*MESH_CVERTLIST {" << std::endl;

		for (std::size_t v = 0; v < surface.vertices.size(); ++v)
		{
			const Vector3& vcol = surface.vertices[v].colour;

			stream << "\t\t\t*MESH_VERTCOL " << v << "\t" << vcol.x() << "\t" << vcol.y() << "\t" << vcol.z() << std::endl;
		}

		stream << "\t\t}" << std::endl;

		// CFaces
		stream << "\t\t*MESH_NUMCVFACES " << (surface.indices.size() / 3) << std::endl;
		stream << "\t\t*MESH_CFACELIST {" << std::endl;

		for (std::size_t i = 0; i + 2 < surface.indices.size(); i += 3)
		{
			std::size_t faceNum = i / 3;

			stream << fmt::format("\t\t\t*MESH_CFACE {:3d}\t{:3d}\t{:3d}\t{:3d}",
				faceNum, surface.indices[i], surface.indices[i + 1], surface.indices[i + 2]) << std::endl;
		}

		stream << "\t\t}" << std::endl;
		
		stream << "\t\t*MESH_NORMALS { " << std::endl;

		for (std::size_t i = 0; i + 2 < surface.indices.size(); i += 3)
		{
			std::size_t faceNum = i / 3;

			const Normal3f& normal1 = surface.vertices[surface.indices[i]].normal;
			const Normal3f& normal2 = surface.vertices[surface.indices[i+1]].normal;
			const Normal3f& normal3 = surface.vertices[surface.indices[i+2]].normal;

			stream << "\t\t\t*MESH_FACENORMAL " << faceNum << "\t" << normal1.x() << "\t" << normal1.y() << "\t" << normal1.z() << std::endl;

			stream << "\t\t\t\t*MESH_VERTEXNORMAL " << surface.indices[i] << "\t" << normal1.x() << "\t" << normal1.y() << "\t" << normal1.z() << std::endl;
			stream << "\t\t\t\t*MESH_VERTEXNORMAL " << surface.indices[i+1] << "\t" << normal2.x() << "\t" << normal2.y() << "\t" << normal2.z() << std::endl;
			stream << "\t\t\t\t*MESH_VERTEXNORMAL " << surface.indices[i+2] << "\t" << normal3.x() << "\t" << normal3.y() << "\t" << normal3.z() << std::endl;
		}

		stream << "\t\t}" << std::endl;

		stream << "\t}" << std::endl;

		stream << "\t*PROP_MOTIONBLUR 0" << std::endl;
		stream << "\t*PROP_CASTSHADOW 1" << std::endl;
		stream << "\t*PROP_RECVSHADOW 1" << std::endl;
		stream << "\t*MATERIAL_REF " << m << std::endl;

		stream << "}" << std::endl;

		++m;
	}
}