tmp<GeomField> coupledInfo<MeshType>::subSetField ( const GeomField& f, const ZeroType& zeroValue, const labelList& internalMapper ) const { typedef typename GeomField::InternalField InternalField; typedef typename GeomField::PatchFieldType PatchFieldType; typedef typename GeomField::GeometricBoundaryField GeomBdyFieldType; typedef typename GeomField::DimensionedInternalField DimInternalField; // Create and map the internal-field values InternalField internalField(f.internalField(), internalMapper); // Create and map the patch field values label nPatches = subMesh().boundary().size(); PtrList<PatchFieldType> patchFields(nPatches); // Define patch type names, assumed to be // common for volume and surface fields word emptyType(emptyPolyPatch::typeName); word processorType(processorPolyPatch::typeName); // Create dummy types for initial field creation forAll(patchFields, patchI) { if (patchI == (nPatches - 1)) { // Artificially set last patch patchFields.set ( patchI, PatchFieldType::New ( emptyType, subMesh().boundary()[patchI], DimInternalField::null() ) ); } else { patchFields.set ( patchI, PatchFieldType::New ( PatchFieldType::calculatedType(), subMesh().boundary()[patchI], DimInternalField::null() ) ); } } // Create new field from pieces tmp<GeomField> subFld ( new GeomField ( IOobject ( "subField_" + f.name(), subMesh().time().timeName(), subMesh(), IOobject::NO_READ, IOobject::NO_WRITE, false ), subMesh(), f.dimensions(), internalField, patchFields ) ); // Set correct references for patch internal fields, // and map values from the supplied geometric field GeomBdyFieldType& bf = subFld().boundaryField(); forAll(bf, patchI) { if (patchI == (nPatches - 1)) { // Artificially set last patch bf.set ( patchI, PatchFieldType::New ( emptyType, subMesh().boundary()[patchI], subFld().dimensionedInternalField() ) ); } else if (isA<processorPolyPatch>(subMesh().boundary()[patchI].patch())) { bf.set ( patchI, PatchFieldType::New ( processorType, subMesh().boundary()[patchI], subFld().dimensionedInternalField() ) ); // Avoid dealing with uninitialised values // by artificially assigning to zero bf[patchI] == zeroValue; } else { bf.set ( patchI, PatchFieldType::New ( f.boundaryField()[patchI], subMesh().boundary()[patchI], subFld().dimensionedInternalField(), subMeshMapper(*this, patchI) ) ); } } return subFld; }
void coupledInfo<MeshType>::setField ( const wordList& fieldNames, const dictionary& fieldDicts, const label internalSize, PtrList<GeomField>& fields ) const { typedef typename GeomField::InternalField InternalField; typedef typename GeomField::PatchFieldType PatchFieldType; typedef typename GeomField::GeometricBoundaryField GeomBdyFieldType; typedef typename GeomField::DimensionedInternalField DimInternalField; // Size up the pointer list fields.setSize(fieldNames.size()); // Define patch type names, assumed to be // common for volume and surface fields word emptyType(emptyPolyPatch::typeName); word processorType(processorPolyPatch::typeName); forAll(fieldNames, i) { // Create and map the patch field values label nPatches = subMesh().boundary().size(); // Create field parts PtrList<PatchFieldType> patchFields(nPatches); // Read dimensions dimensionSet dimSet ( fieldDicts.subDict(fieldNames[i]).lookup("dimensions") ); // Read the internal field InternalField internalField ( "internalField", fieldDicts.subDict(fieldNames[i]), internalSize ); // Create dummy types for initial field creation forAll(patchFields, patchI) { if (patchI == (nPatches - 1)) { // Artificially set last patch patchFields.set ( patchI, PatchFieldType::New ( emptyType, subMesh().boundary()[patchI], DimInternalField::null() ) ); } else { patchFields.set ( patchI, PatchFieldType::New ( PatchFieldType::calculatedType(), subMesh().boundary()[patchI], DimInternalField::null() ) ); } } // Create field with dummy patches fields.set ( i, new GeomField ( IOobject ( fieldNames[i], subMesh().time().timeName(), subMesh(), IOobject::NO_READ, IOobject::NO_WRITE, false ), subMesh(), dimSet, internalField, patchFields ) ); // Set correct references for patch internal fields, // and fetch values from the supplied geometric field dictionaries GeomBdyFieldType& bf = fields[i].boundaryField(); forAll(bf, patchI) { if (patchI == (nPatches - 1)) { // Artificially set last patch bf.set ( patchI, PatchFieldType::New ( emptyType, subMesh().boundary()[patchI], fields[i].dimensionedInternalField() ) ); } else if (isA<processorPolyPatch>(subMesh().boundary()[patchI].patch())) { bf.set ( patchI, PatchFieldType::New ( processorType, subMesh().boundary()[patchI], fields[i].dimensionedInternalField() ) ); } else { bf.set ( patchI, PatchFieldType::New ( subMesh().boundary()[patchI], fields[i].dimensionedInternalField(), fieldDicts.subDict ( fieldNames[i] ).subDict("boundaryField").subDict ( subMesh().boundary()[patchI].name() ) ) ); } } }
NzSubMesh* NzMesh::BuildSubMesh(const NzPrimitive& primitive, const NzMeshParams& params) { #if NAZARA_UTILITY_SAFE if (!m_impl) { NazaraError("Mesh not created"); return nullptr; } if (m_impl->animationType != nzAnimationType_Static) { NazaraError("Mesh must be static"); return nullptr; } if (!params.IsValid()) { NazaraError("Parameters must be valid"); return nullptr; } #endif NzBoxf aabb; std::unique_ptr<NzIndexBuffer> indexBuffer; std::unique_ptr<NzVertexBuffer> vertexBuffer; NzMatrix4f matrix(primitive.matrix); matrix.ApplyScale(params.scale); NzVertexDeclaration* declaration = NzVertexDeclaration::Get(nzVertexLayout_XYZ_Normal_UV_Tangent); switch (primitive.type) { case nzPrimitiveType_Box: { unsigned int indexCount; unsigned int vertexCount; NzComputeBoxIndexVertexCount(primitive.box.subdivision, &indexCount, &vertexCount); indexBuffer.reset(new NzIndexBuffer(vertexCount > std::numeric_limits<nzUInt16>::max(), indexCount, params.storage, nzBufferUsage_Static)); indexBuffer->SetPersistent(false); vertexBuffer.reset(new NzVertexBuffer(declaration, vertexCount, params.storage, nzBufferUsage_Static)); vertexBuffer->SetPersistent(false); NzBufferMapper<NzVertexBuffer> vertexMapper(vertexBuffer.get(), nzBufferAccess_WriteOnly); NzIndexMapper indexMapper(indexBuffer.get(), nzBufferAccess_WriteOnly); NzGenerateBox(primitive.box.lengths, primitive.box.subdivision, matrix, primitive.textureCoords, static_cast<NzMeshVertex*>(vertexMapper.GetPointer()), indexMapper.begin(), &aabb); break; } case nzPrimitiveType_Cone: { unsigned int indexCount; unsigned int vertexCount; NzComputeConeIndexVertexCount(primitive.cone.subdivision, &indexCount, &vertexCount); indexBuffer.reset(new NzIndexBuffer(vertexCount > std::numeric_limits<nzUInt16>::max(), indexCount, params.storage, nzBufferUsage_Static)); indexBuffer->SetPersistent(false); vertexBuffer.reset(new NzVertexBuffer(declaration, vertexCount, params.storage, nzBufferUsage_Static)); vertexBuffer->SetPersistent(false); NzBufferMapper<NzVertexBuffer> vertexMapper(vertexBuffer.get(), nzBufferAccess_WriteOnly); NzIndexMapper indexMapper(indexBuffer.get(), nzBufferAccess_WriteOnly); NzGenerateCone(primitive.cone.length, primitive.cone.radius, primitive.cone.subdivision, matrix, primitive.textureCoords, static_cast<NzMeshVertex*>(vertexMapper.GetPointer()), indexMapper.begin(), &aabb); break; } case nzPrimitiveType_Plane: { unsigned int indexCount; unsigned int vertexCount; NzComputePlaneIndexVertexCount(primitive.plane.subdivision, &indexCount, &vertexCount); indexBuffer.reset(new NzIndexBuffer(vertexCount > std::numeric_limits<nzUInt16>::max(), indexCount, params.storage, nzBufferUsage_Static)); indexBuffer->SetPersistent(false); vertexBuffer.reset(new NzVertexBuffer(declaration, vertexCount, params.storage, nzBufferUsage_Static)); vertexBuffer->SetPersistent(false); NzBufferMapper<NzVertexBuffer> vertexMapper(vertexBuffer.get(), nzBufferAccess_WriteOnly); NzIndexMapper indexMapper(indexBuffer.get(), nzBufferAccess_WriteOnly); NzGeneratePlane(primitive.plane.subdivision, primitive.plane.size, matrix, primitive.textureCoords, static_cast<NzMeshVertex*>(vertexMapper.GetPointer()), indexMapper.begin(), &aabb); break; } case nzPrimitiveType_Sphere: { switch (primitive.sphere.type) { case nzSphereType_Cubic: { unsigned int indexCount; unsigned int vertexCount; NzComputeCubicSphereIndexVertexCount(primitive.sphere.cubic.subdivision, &indexCount, &vertexCount); indexBuffer.reset(new NzIndexBuffer(vertexCount > std::numeric_limits<nzUInt16>::max(), indexCount, params.storage, nzBufferUsage_Static)); indexBuffer->SetPersistent(false); vertexBuffer.reset(new NzVertexBuffer(declaration, vertexCount, params.storage, nzBufferUsage_Static)); vertexBuffer->SetPersistent(false); NzBufferMapper<NzVertexBuffer> vertexMapper(vertexBuffer.get(), nzBufferAccess_WriteOnly); NzIndexMapper indexMapper(indexBuffer.get(), nzBufferAccess_WriteOnly); NzGenerateCubicSphere(primitive.sphere.size, primitive.sphere.cubic.subdivision, matrix, primitive.textureCoords, static_cast<NzMeshVertex*>(vertexMapper.GetPointer()), indexMapper.begin(), &aabb); break; } case nzSphereType_Ico: { unsigned int indexCount; unsigned int vertexCount; NzComputeIcoSphereIndexVertexCount(primitive.sphere.ico.recursionLevel, &indexCount, &vertexCount); indexBuffer.reset(new NzIndexBuffer(vertexCount > std::numeric_limits<nzUInt16>::max(), indexCount, params.storage, nzBufferUsage_Static)); indexBuffer->SetPersistent(false); vertexBuffer.reset(new NzVertexBuffer(declaration, vertexCount, params.storage, nzBufferUsage_Static)); vertexBuffer->SetPersistent(false); NzBufferMapper<NzVertexBuffer> vertexMapper(vertexBuffer.get(), nzBufferAccess_WriteOnly); NzIndexMapper indexMapper(indexBuffer.get(), nzBufferAccess_WriteOnly); NzGenerateIcoSphere(primitive.sphere.size, primitive.sphere.ico.recursionLevel, matrix, primitive.textureCoords, static_cast<NzMeshVertex*>(vertexMapper.GetPointer()), indexMapper.begin(), &aabb); break; } case nzSphereType_UV: { unsigned int indexCount; unsigned int vertexCount; NzComputeUvSphereIndexVertexCount(primitive.sphere.uv.sliceCount, primitive.sphere.uv.stackCount, &indexCount, &vertexCount); indexBuffer.reset(new NzIndexBuffer(vertexCount > std::numeric_limits<nzUInt16>::max(), indexCount, params.storage, nzBufferUsage_Static)); indexBuffer->SetPersistent(false); vertexBuffer.reset(new NzVertexBuffer(declaration, vertexCount, params.storage, nzBufferUsage_Static)); vertexBuffer->SetPersistent(false); NzBufferMapper<NzVertexBuffer> vertexMapper(vertexBuffer.get(), nzBufferAccess_WriteOnly); NzIndexMapper indexMapper(indexBuffer.get(), nzBufferAccess_WriteOnly); NzGenerateUvSphere(primitive.sphere.size, primitive.sphere.uv.sliceCount, primitive.sphere.uv.stackCount, matrix, primitive.textureCoords, static_cast<NzMeshVertex*>(vertexMapper.GetPointer()), indexMapper.begin(), &aabb); break; } } break; } } std::unique_ptr<NzStaticMesh> subMesh(new NzStaticMesh(this)); if (!subMesh->Create(vertexBuffer.get())) { NazaraError("Failed to create StaticMesh"); return nullptr; } vertexBuffer.release(); if (params.optimizeIndexBuffers) indexBuffer->Optimize(); subMesh->SetIndexBuffer(indexBuffer.get()); indexBuffer.release(); subMesh->SetAABB(aabb); AddSubMesh(subMesh.get()); return subMesh.release(); }