public VertexBufferBuilder(int positionsCount, VertexDefinition vd) { _vd = vd; _taken = new bool[positionsCount]; _vertices = new List <VertexCache> [positionsCount]; _vertexBufferData = new MemoryStream(positionsCount * vd.Size); }
public void CreateVertexBuffer <T>(Span <T> data) where T : unmanaged { _vd = VertexDefinition.GetDefinition <T>(); _vb = new VertexBuffer(_vd); _vb.SetData(data); }
public Vector2I UpdateVertexArray(string text, ref VertexDefinition.PositionTextureColor[] vertices, ref Buffer vertexBuffer, Color defaultColor, List<TexturedRectangle> icons, int positionX = 0, int positionY = 0) { icons.Clear(); Color color = defaultColor; int width = 0; int maxWidth = 0; int height = Characters.First().Value.height; int maxHeight = height; for (int i = 0; i < text.Length; i++) { char letter = text[i]; if (letter == '\n') { maxWidth = Math.Max(maxWidth, width); width = 0; positionX = 0; positionY += height; maxHeight += height; continue; } if (letter == '[') { if (text[i + 1] == '[') continue; string token = text.Substring(i + 1, text.IndexOf(']', i + 1) - (i + 1)); if (!ColorParser.TryParse(token, out color)) { if (token == "-") color = defaultColor; else if (token == "gold") { icons.Add(new TexturedRectangle(_context, _context.TextureManager.Create("gold.png", "Data/UI/Icons/"), new Vector2I(height, height))); positionX += height + 1; width += height + 1; } else throw new InvalidOperationException("Unexpected token : " + token); } i = text.IndexOf(']', i + 1); continue; } Character c = Characters[letter]; Vector4 colorAsVector = color.ToVector4(); vertices[i * 4] = new VertexDefinition.PositionTextureColor { position = new Vector3(positionX, positionY, 0.0f), texture = new Vector2(c.uLeft, c.vTop), color = colorAsVector }; //Top left vertices[i * 4 + 1] = new VertexDefinition.PositionTextureColor { position = new Vector3(positionX + c.width, positionY + c.height, 0.0f), texture = new Vector2(c.uRight, c.vBottom), color = colorAsVector }; //Right bottom vertices[i * 4 + 2] = new VertexDefinition.PositionTextureColor { position = new Vector3(positionX, positionY + c.height, 0.0f), texture = new Vector2(c.uLeft, c.vBottom), color = colorAsVector }; //Left bottom vertices[i * 4 + 3] = new VertexDefinition.PositionTextureColor { position = new Vector3(positionX + c.width, positionY, 0.0f), texture = new Vector2(c.uRight, c.vTop), color = colorAsVector }; //Top right positionX += c.width + 1; width += c.width + 1; } DataStream mappedResource; _context.DirectX.Device.ImmediateContext.MapSubresource(vertexBuffer, MapMode.WriteDiscard, SharpDX.Direct3D11.MapFlags.None, out mappedResource); mappedResource.WriteRange(vertices); _context.DirectX.Device.ImmediateContext.UnmapSubresource(vertexBuffer, 0); return new Vector2I(Math.Max(maxWidth, width), maxHeight); }
protected override void DefineLocation(VertexDefinition definition, Renderable target, Type vertexType) { definition.Map(vertexType, "vPos", VertexSpecialField.Position); definition.Map(vertexType, "vNormal", VertexSpecialField.Normal); definition.Map(vertexType, "vUV", VertexSpecialField.UV); definition.Map(vertexType, "bone", VertexSpecialField.Bone); definition.Map(vertexType, "weight", VertexSpecialField.Weight); definition.Map(vertexType, "vtexIndex", VertexSpecialField.TextureIndex); }
protected virtual VertexDefinition ReadVertexDefinition() { var vertexDefinition = new VertexDefinition(); vertexDefinition.Variable = (VertexDefinition.VariableEnum)fileData[iPos]; vertexDefinition.VariableType = (VertexDefinition.VariableTypeEnum)fileData[iPos + 1]; vertexDefinition.Offset = (int)fileData[iPos + 2]; ColoredConsole.WriteLine("{0:x8} {1} {2}", (object)iPos, (object)vertexDefinition.VariableType.ToString(), (object)vertexDefinition.Variable.ToString()); iPos += 3; return(vertexDefinition); }
public void OnDrawGizmos() { if (MeshFilter.mesh == null) { MeshFilter.mesh = new Mesh(); } if (Points == null || Points.Count < 3) { return; } VertList = new List <VertexDefinition>(); float colorNum = 0f; var lastVert = new VertexDefinition(Points.First().position, ColorUtility.HsvtoRgb(0, .8f, 1f)); foreach (var point in Points) { var thisVert = new VertexDefinition(point.position, ColorUtility.HsvtoRgb(colorNum, .8f, 1f), lastVert.Position, point.position); colorNum += COLOR_MOD; VertList.Add(thisVert); lastVert.NextPosition = thisVert.Position; lastVert = thisVert; } // last point required here to complete triangle MeshFilter.mesh.Clear(); MeshFilter.mesh.vertices = VertList.Select(vertex => vertex.Position).ToArray(); MeshFilter.mesh.colors = VertList.Select(vertex => vertex.Color).ToArray(); MeshFilter.mesh.normals = VertList.Select(vertex => vertex.NextPosition - vertex.Position).ToArray(); MeshFilter.mesh.tangents = VertList.Select(vertex => (vertex.LastPosition - vertex.Position).ConvertToVector4()).ToArray(); var indices = new List <int>(); for (var i = 0; i < VertList.Count; i++) { indices.Add(i); } MeshFilter.mesh.SetIndices(indices.ToArray(), MeshTopology.LineStrip, 0); MeshFilter.mesh.UploadMeshData(false); }
public override Mesh CreateMesh() { return(new Mesh(VertexDefinition.GetDefinition <SkinnedVertex>())); }
protected virtual VertexList ReadVertexList(int numberofvertices) { var vertexList = new VertexList(); if (fileData[iPos] != (byte)0) { var vertexDefinition = new VertexDefinition(); vertexDefinition.Variable = VertexDefinition.VariableEnum.position; vertexDefinition.VariableType = (VertexDefinition.VariableTypeEnum)fileData[iPos]; vertexList.VertexDefinitions.Add(vertexDefinition); ColoredConsole.WriteLine("{0:x8} {1} {2}", (object)iPos, (object)vertexDefinition.VariableType.ToString(), (object)vertexDefinition.Variable.ToString()); } iPos += 2; if (fileData[iPos] != (byte)0) { var vertexDefinition = new VertexDefinition(); vertexDefinition.Variable = VertexDefinition.VariableEnum.normal; vertexDefinition.VariableType = (VertexDefinition.VariableTypeEnum)fileData[iPos]; vertexList.VertexDefinitions.Add(vertexDefinition); ColoredConsole.WriteLine("{0:x8} {1} {2}", (object)iPos, (object)vertexDefinition.VariableType.ToString(), (object)vertexDefinition.Variable.ToString()); } iPos += 2; if (fileData[iPos] != (byte)0) { var vertexDefinition = new VertexDefinition(); vertexDefinition.Variable = VertexDefinition.VariableEnum.colorSet0; vertexDefinition.VariableType = (VertexDefinition.VariableTypeEnum)fileData[iPos]; vertexList.VertexDefinitions.Add(vertexDefinition); ColoredConsole.WriteLine("{0:x8} {1} {2}", (object)iPos, (object)vertexDefinition.VariableType.ToString(), (object)vertexDefinition.Variable.ToString()); } iPos += 2; if (fileData[iPos] != (byte)0) { var vertexDefinition = new VertexDefinition(); vertexDefinition.Variable = VertexDefinition.VariableEnum.tangent; vertexDefinition.VariableType = (VertexDefinition.VariableTypeEnum)fileData[iPos]; vertexList.VertexDefinitions.Add(vertexDefinition); ColoredConsole.WriteLine("{0:x8} {1} {2}", (object)iPos, (object)vertexDefinition.VariableType.ToString(), (object)vertexDefinition.Variable.ToString()); } iPos += 2; if (fileData[iPos] != (byte)0) { var vertexDefinition = new VertexDefinition(); vertexDefinition.Variable = VertexDefinition.VariableEnum.colorSet1; vertexDefinition.VariableType = (VertexDefinition.VariableTypeEnum)fileData[iPos]; vertexList.VertexDefinitions.Add(vertexDefinition); ColoredConsole.WriteLine("{0:x8} {1} {2}", (object)iPos, (object)vertexDefinition.VariableType.ToString(), (object)vertexDefinition.Variable.ToString()); } iPos += 2; if (fileData[iPos] != (byte)0) { var vertexDefinition = new VertexDefinition(); vertexDefinition.Variable = VertexDefinition.VariableEnum.uvSet01; vertexDefinition.VariableType = (VertexDefinition.VariableTypeEnum)fileData[iPos]; vertexList.VertexDefinitions.Add(vertexDefinition); ColoredConsole.WriteLine("{0:x8} {1} {2}", (object)iPos, (object)vertexDefinition.VariableType.ToString(), (object)vertexDefinition.Variable.ToString()); } iPos += 2; iPos += 2; if (fileData[iPos] != (byte)0) { var vertexDefinition = new VertexDefinition(); vertexDefinition.Variable = VertexDefinition.VariableEnum.uvSet2; vertexDefinition.VariableType = (VertexDefinition.VariableTypeEnum)fileData[iPos]; vertexList.VertexDefinitions.Add(vertexDefinition); ColoredConsole.WriteLine("{0:x8} {1} {2}", (object)iPos, (object)vertexDefinition.VariableType.ToString(), (object)vertexDefinition.Variable.ToString()); } iPos += 2; iPos += 2; if (fileData[iPos] != (byte)0) { var vertexDefinition = new VertexDefinition(); vertexDefinition.Variable = VertexDefinition.VariableEnum.blendIndices0; vertexDefinition.VariableType = (VertexDefinition.VariableTypeEnum)fileData[iPos]; vertexList.VertexDefinitions.Add(vertexDefinition); ColoredConsole.WriteLine("{0:x8} {1} {2}", (object)iPos, (object)vertexDefinition.VariableType.ToString(), (object)vertexDefinition.Variable.ToString()); } iPos += 2; if (fileData[iPos] != (byte)0) { var vertexDefinition = new VertexDefinition(); vertexDefinition.Variable = VertexDefinition.VariableEnum.blendWeight0; vertexDefinition.VariableType = (VertexDefinition.VariableTypeEnum)fileData[iPos]; vertexList.VertexDefinitions.Add(vertexDefinition); ColoredConsole.WriteLine("{0:x8} {1} {2}", (object)iPos, (object)vertexDefinition.VariableType.ToString(), (object)vertexDefinition.Variable.ToString()); } iPos += 2; if (fileData[iPos] != (byte)0) { var vertexDefinition = new VertexDefinition(); vertexDefinition.Variable = VertexDefinition.VariableEnum.lightDirSet; vertexDefinition.VariableType = (VertexDefinition.VariableTypeEnum)fileData[iPos]; vertexList.VertexDefinitions.Add(vertexDefinition); ColoredConsole.WriteLine("{0:x8} {1} {2}", (object)iPos, (object)vertexDefinition.VariableType.ToString(), (object)vertexDefinition.Variable.ToString()); } iPos += 2; if (fileData[iPos] != (byte)0) { var vertexDefinition = new VertexDefinition(); vertexDefinition.Variable = VertexDefinition.VariableEnum.lightColSet; vertexDefinition.VariableType = (VertexDefinition.VariableTypeEnum)fileData[iPos]; vertexList.VertexDefinitions.Add(vertexDefinition); ColoredConsole.WriteLine("{0:x8} {1} {2}", (object)iPos, (object)vertexDefinition.VariableType.ToString(), (object)vertexDefinition.Variable.ToString()); } iPos += 2; iPos += 6; ColoredConsole.WriteLine("{0:x8} Number of Vertices: {1:x8}", (object)iPos, (object)numberofvertices); for (var index = 0; index < numberofvertices; ++index) { vertexList.Vertices.Add(ReadVertex(vertexList.VertexDefinitions)); } return(vertexList); }
void IDefinition.FromArray(byte[] buffer) { BinaryReader bin = new BinaryReader(new MemoryStream(buffer)); VertexType = (VertexDefinition)bin.ReadInt32(); VertexCount = bin.ReadUInt16(); TriangleCount = bin.ReadUInt16(); bin.BaseStream.Seek(16, SeekOrigin.Current); Compression = (CompressionFlags)bin.ReadUInt16(); bin.BaseStream.Seek(28, SeekOrigin.Current); RawOffset = bin.ReadUInt32(); RawSize = bin.ReadUInt32(); HeaderSize = bin.ReadUInt32(); RawDataSize = bin.ReadUInt32(); }
public VertexBuffer(VertexDefinition vd, byte[] data) : base(data) { _vd = vd; _vertexCount = data.Length / vd.Size; }
public VertexBuffer(VertexDefinition vd) { _vd = vd; }
protected override void DefineLocation(VertexDefinition definition, Renderable target, Type vertexType) { definition.Map(vertexType, "_pos", VertexSpecialField.Position); }
private void UpdateOverlayVertexBuffer(DeviceContext deviceContext, Resource overlayVertexBuffer, VertexDefinition.PositionColor[] vertices, int vertexCount) { var dataBox = deviceContext.MapSubresource(overlayVertexBuffer, 0, MapMode.WriteDiscard, MapFlags.None); Utilities.Write(dataBox.DataPointer, vertices, 0, vertexCount); deviceContext.UnmapSubresource(overlayVertexBuffer, 0); }
public void Render() { var variantName = Object.DefaultModelVariant != StringId.Invalid ? CacheContext.GetString(Object.DefaultModelVariant) : "default"; var modelVariant = Model.Variants.FirstOrDefault(v => (CacheContext.GetString(v.Name) ?? v.Name.ToString()) == variantName); if (modelVariant == null && Model.Variants.Count > 0) { modelVariant = Model.Variants.First(); } UpdateTransform(); Device.Transform.World = World; foreach (var region in modelVariant.Regions) { if (region.RenderModelRegionIndex >= RenderModel.Regions.Count) { continue; } var renderModelRegion = RenderModel.Regions[region.RenderModelRegionIndex]; if (region.Permutations.Count == 0) { continue; } var permutation = region.Permutations[0]; if (permutation.RenderModelPermutationIndex < 0 || permutation.RenderModelPermutationIndex >= renderModelRegion.Permutations.Count) { continue; } var renderModelPermutation = renderModelRegion.Permutations[permutation.RenderModelPermutationIndex]; var meshIndex = renderModelPermutation.MeshIndex; var meshCount = renderModelPermutation.MeshCount; var regionName = CacheContext.GetString(region.Name) ?? region.Name.ToString(); var permutationName = CacheContext.GetString(permutation.Name) ?? permutation.Name.ToString(); for (var currentMeshIndex = 0; currentMeshIndex < meshCount; currentMeshIndex++) { var mesh = RenderModel.Geometry.Meshes[meshIndex + currentMeshIndex]; var renderVertex = VertexDefinition.Get(mesh.Type); var streamTypes = renderVertex.GetStreamTypes(); var streamIndex = streamTypes.First().Key; var primitiveType = D3DPrimitiveType.TriangleList; switch (mesh.IndexBufferType) { case TagPrimitiveType.PointList: primitiveType = D3DPrimitiveType.PointList; break; case TagPrimitiveType.LineList: primitiveType = D3DPrimitiveType.LineList; break; case TagPrimitiveType.LineStrip: primitiveType = D3DPrimitiveType.LineStrip; break; case TagPrimitiveType.TriangleList: primitiveType = D3DPrimitiveType.TriangleList; break; case TagPrimitiveType.TriangleFan: primitiveType = D3DPrimitiveType.TriangleFan; break; case TagPrimitiveType.TriangleStrip: primitiveType = D3DPrimitiveType.TriangleStrip; break; } Device.VertexDeclaration = renderVertex.GetDeclaration(Device); Device.SetStreamSource(streamTypes.First().Key, VertexBuffers[mesh.VertexBufferIndices[streamIndex]], 0); Device.Indices = IndexBuffers[mesh.IndexBufferIndices.Where(index => index != ushort.MaxValue).First()]; foreach (var part in mesh.Parts) { if (part.MaterialIndex != -1) { var material = Materials[part.MaterialIndex]; Device.RenderState.AlphaBlendEnable = (part.TypeNew == TagTool.Geometry.Mesh.Part.PartTypeNew.Transparent); foreach (var entry in material.Textures) { var name = entry.Key; if (name.StartsWith("diffuse_map") || name.StartsWith("base_map") || name == "foam_texture") { Device.SetTexture(0, entry.Value.Texture); break; } } Device.TextureState[0].ColorOperation = TextureOperation.Modulate; Device.TextureState[0].ColorArgument1 = TextureArgument.TextureColor; Device.TextureState[0].ColorArgument2 = TextureArgument.Current; Device.RenderState.FillMode = FillMode.Solid; } for (var currentSubPartIndex = 0; currentSubPartIndex < part.SubPartCount; currentSubPartIndex++) { var subPart = mesh.SubParts[part.FirstSubPartIndex + currentSubPartIndex]; Device.DrawIndexedPrimitives(primitiveType, 0, 0, subPart.VertexCount, subPart.FirstIndex, subPart.IndexCount - (primitiveType == D3DPrimitiveType.TriangleStrip ? 2 : 0)); } } } } }
public virtual Mesh CreateMesh() { return(new Mesh(VertexDefinition.GetDefinition <MeshVertex>())); }
protected override void DefineLocation(VertexDefinition definition, Control target, Type vertexType) { definition.Map(vertexType, "_vPos", VertexSpecialField.Position); definition.Map(vertexType, "_vUV", VertexSpecialField.UV); }
public Mesh(VertexDefinition vd) { _vd = vd; _vb = new VertexBuffer(vd); }
public RenderObject(D3DDevice device, HaloOnlineCacheContext cacheContext, GameObject definition, RealPoint3d position, RealEulerAngles3d rotation) { if (device == null) { throw new ArgumentNullException(nameof(device)); } else if (cacheContext == null) { throw new ArgumentNullException(nameof(cacheContext)); } else if (definition == null) { throw new ArgumentNullException(nameof(definition)); } Device = device; CacheContext = cacheContext; Object = definition; Position = position; Rotation = rotation; UpdateTransform(); using (var cacheStream = CacheContext.OpenTagCacheRead()) { if (Object.Model == null) { throw new NullReferenceException(nameof(Object.Model)); } Model = CacheContext.Deserialize <Model>(new TagSerializationContext(cacheStream, CacheContext, Object.Model)); if (Model.RenderModel == null) { throw new NullReferenceException(nameof(Model.RenderModel)); } RenderModel = CacheContext.Deserialize <RenderModel>(new TagSerializationContext(cacheStream, CacheContext, Model.RenderModel)); if (Model.Variants == null || Model.Variants.Count == 0) { var modelVariant = new Model.Variant { Name = CacheContext.GetStringId("default"), Regions = new List <Model.Variant.Region>() }; foreach (var region in RenderModel.Regions) { var modelRegion = new Model.Variant.Region { Name = region.Name, RenderModelRegionIndex = (sbyte)RenderModel.Regions.IndexOf(region), Permutations = new List <Model.Variant.Region.Permutation>() }; foreach (var permutation in region.Permutations) { modelRegion.Permutations.Add(new Model.Variant.Region.Permutation { Name = modelVariant.Name, RenderModelPermutationIndex = (sbyte)region.Permutations.IndexOf(permutation) }); } modelVariant.Regions.Add(modelRegion); } Model.Variants = new List <Model.Variant> { modelVariant }; } Materials = new List <RenderMaterial>(); foreach (var material in RenderModel.Materials) { Materials.Add(new RenderMaterial(device, CacheContext, material)); } if (RenderModel.Geometry.Resource == null) { throw new NullReferenceException(nameof(RenderModel.Geometry.Resource)); } RenderGeometryResource = CacheContext.Deserialize <RenderGeometryApiResourceDefinition>(RenderModel.Geometry.Resource); using (var resourceStream = new MemoryStream()) using (var reader = new BinaryReader(resourceStream)) { CacheContext.ExtractResource(RenderModel.Geometry.Resource, resourceStream); VertexBuffers = new Dictionary <int, VertexBuffer>(); IndexBuffers = new Dictionary <int, IndexBuffer>(); var compression = RenderModel.Geometry.Compression[0]; foreach (var mesh in RenderModel.Geometry.Meshes) { var renderVertex = VertexDefinition.Get(mesh.Type); var streamTypes = renderVertex.GetStreamTypes(); foreach (var streamEntry in streamTypes) { var vertexBufferIndex = mesh.VertexBufferIndices[streamEntry.Key]; if (vertexBufferIndex == ushort.MaxValue || VertexBuffers.ContainsKey(vertexBufferIndex)) { continue; } var vbDef = RenderGeometryResource.VertexBuffers[vertexBufferIndex].Definition; var vb = new VertexBuffer(streamEntry.Value, vbDef.Data.Size, device, Usage.DoNotClip, renderVertex.GetStreamFormat(streamEntry.Key), Pool.Managed); var vbData = vb.Lock(0, vbDef.Data.Size, LockFlags.None); resourceStream.Position = vbDef.Data.Address.Offset; var vertices = Array.CreateInstance(streamEntry.Value, vbDef.Count); for (var i = 0; i < vbDef.Count; i++) { var handle = GCHandle.Alloc(reader.ReadBytes(Marshal.SizeOf(streamEntry.Value)), GCHandleType.Pinned); var vertex = Marshal.PtrToStructure(handle.AddrOfPinnedObject(), streamEntry.Value); var positionField = streamEntry.Value.GetField("Position"); if (positionField != null) { var xyz = (Vector3)positionField.GetValue(vertex); positionField.SetValue(vertex, new Vector3( xyz.X * compression.X.Length + compression.X.Lower, xyz.Y * compression.Y.Length + compression.Y.Lower, xyz.Z * compression.Z.Length + compression.Z.Lower)); } var texcoordField = streamEntry.Value.GetField("Texcoord"); if (texcoordField != null) { var uv = (Vector2)texcoordField.GetValue(vertex); texcoordField.SetValue(vertex, new Vector2( uv.X * compression.U.Length + compression.U.Lower, uv.Y * compression.V.Length + compression.V.Lower)); } vertices.SetValue(vertex, i); handle.Free(); } vbData.Write(vertices); vb.Unlock(); VertexBuffers[vertexBufferIndex] = vb; } foreach (var indexBufferIndex in mesh.IndexBufferIndices) { if (indexBufferIndex == ushort.MaxValue || IndexBuffers.ContainsKey(indexBufferIndex)) { continue; } var ibDef = RenderGeometryResource.IndexBuffers[indexBufferIndex].Definition; switch (ibDef.Format) { case IndexBufferFormat.PointList: mesh.IndexBufferType = TagPrimitiveType.PointList; break; case IndexBufferFormat.LineList: mesh.IndexBufferType = TagPrimitiveType.LineList; break; case IndexBufferFormat.LineStrip: mesh.IndexBufferType = TagPrimitiveType.LineStrip; break; case IndexBufferFormat.TriangleList: mesh.IndexBufferType = TagPrimitiveType.TriangleList; break; case IndexBufferFormat.TriangleFan: mesh.IndexBufferType = TagPrimitiveType.TriangleFan; break; case IndexBufferFormat.TriangleStrip: mesh.IndexBufferType = TagPrimitiveType.TriangleStrip; break; } var ib = new IndexBuffer(device, ibDef.Data.Size, Usage.DoNotClip, Pool.Managed, true); var ibData = ib.Lock(0, ibDef.Data.Size, LockFlags.None); resourceStream.Position = ibDef.Data.Address.Offset; var indices = new ushort[ibDef.Data.Size / 2]; for (var i = 0; i < ibDef.Data.Size / 2; i++) { indices[i] = reader.ReadUInt16(); } ibData.Write(indices); ib.Unlock(); IndexBuffers[indexBufferIndex] = ib; } } } } }
public void CreateSurface(NameValueMap nv) { var T0 = DateTime.Now; var T1 = DateTime.Now; var T2 = DateTime.Now; var N = 100; var Nu = N; // number of u control points var Lx = 10.0; // x-extent in cm var Nv = N; // number of v control points var Ly = 10.0; // y-extent in cm var tg = mApp.TransientGeometry; var partDoc = (PartDocument)mApp.ActiveDocument; var cd = partDoc.ComponentDefinition; var features = cd.Features; int dimU = 3 + Nu; int dimV = 3 + Nv; int dimC = 3 * Nu * Nv; var uKnots = new double[dimU]; var vKnots = new double[dimV]; var controls = new double[dimC]; // NOTE: The Inventor documentation does not seem to mention this, // but providing an empty array of weights apparently causes // Inventor to assume all points are equally weighted. //var weights = new double[Nu * Nv]; var weights = new double[0]; for (int i = 0; i <= 2; ++i) { uKnots[i] = vKnots[i] = 0.0; } for (int u = 3; u < Nu; ++u) { uKnots[u] = (u - 2) * (1.0f / (Nu - 2)); } for (int v = 3; v < Nv; ++v) { vKnots[v] = (v - 2) * (1.0f / (Nv - 2)); } for (int u = Nu; u < Nu + 3; ++u) { uKnots[u] = 1.0; } for (int v = Nv; v < Nv + 3; ++v) { vKnots[v] = 1.0; } for (int u = 0; u < Nu; ++u) { var x = u * Lx / (Nu - 1); for (int v = 0; v < Nv; ++v) { var y = v * Ly / (Nv - 1); var idx = 3 * (v * Nu + u); controls[idx] = x; controls[idx + 1] = y; var r = Math.Sqrt(x * x + y * y); controls[idx + 2] = 0.3 * Math.Cos(2 * r); } } var polesu0 = new double[3 * Nv]; // u = 0 edge var polesuN = new double[3 * Nv]; // u = Nu-1 edge var polesv0 = new double[3 * Nu]; // v = 0 edge var polesvN = new double[3 * Nu]; // v = Nv-1 edge for (int u = 0; u < Nu; ++u) { // The v0 edge runs from (0, 0) to (Nu - 1, 0) int v0base = 3 * u; // The vN edge runs from (Nu - 1, Nv - 1) to (0, Nv - 1) int vNbase = 3 * ((Nu - 1 - u) + Nu * (Nv - 1)); for (int k = 0; k < 3; ++k) { polesv0[3 * u + k] = controls[v0base + k]; polesvN[3 * u + k] = controls[vNbase + k]; } } for (int v = 0; v < Nv; ++v) { // The u0 edge runs from (0, Nv - 1) to (0, 0) int u0base = 3 * Nu * (Nv - 1 - v); // The uN edge runs from (Nu - 1, 0) to (Nu - 1, Nv - 1) int uNbase = 3 * (Nu - 1 + Nu * v); for (int k = 0; k < 3; ++k) { polesu0[3 * v + k] = controls[u0base + k]; polesuN[3 * v + k] = controls[uNbase + k]; } } var order = new int[2] { 3, 3 }; var isPeriodic = new bool[2] { false, false }; var transaction = mApp.TransactionManager.StartTransaction(mApp.ActiveDocument, "Create B-Spline Surface"); try { var curvev0 = tg.CreateBSplineCurve(3, ref polesv0, ref uKnots, ref weights, isPeriodic[0]); var curveuN = tg.CreateBSplineCurve(3, ref polesuN, ref vKnots, ref weights, isPeriodic[1]); // TODO: Should the knots be reversed for curvevN and curve u0? // We can get away with not reversing them now because they are always symmetric. var curvevN = tg.CreateBSplineCurve(3, ref polesvN, ref uKnots, ref weights, isPeriodic[0]); var curveu0 = tg.CreateBSplineCurve(3, ref polesu0, ref vKnots, ref weights, isPeriodic[1]); var topSurface = tg.CreateBSplineSurface(ref order, ref controls, ref uKnots, ref vKnots, ref weights, ref isPeriodic); if (topSurface == null) { throw new Exception("TransientGeometry.CreateBSplineSurface returned null"); } var bodyDef = mApp.TransientBRep.CreateSurfaceBodyDefinition(); var corners = new VertexDefinition[4]; corners[0] = bodyDef.VertexDefinitions.Add(tg.CreatePoint(controls[0], controls[1], controls[2])); int c1 = 3 * (Nu - 1); corners[1] = bodyDef.VertexDefinitions.Add(tg.CreatePoint(controls[c1], controls[c1 + 1], controls[c1 + 2])); int c2 = c1 + 3 * Nu * (Nv - 1); corners[2] = bodyDef.VertexDefinitions.Add(tg.CreatePoint(controls[c2], controls[c2 + 1], controls[c2 + 2])); int c3 = 3 * Nu * (Nv - 1); corners[3] = bodyDef.VertexDefinitions.Add(tg.CreatePoint(controls[c3], controls[c3 + 1], controls[c3 + 2])); var edges = new EdgeDefinition[4]; edges[0] = bodyDef.EdgeDefinitions.Add(corners[0], corners[1], curvev0); edges[1] = bodyDef.EdgeDefinitions.Add(corners[1], corners[2], curveuN); edges[2] = bodyDef.EdgeDefinitions.Add(corners[2], corners[3], curvevN); edges[3] = bodyDef.EdgeDefinitions.Add(corners[3], corners[0], curveu0); var lumpDef = bodyDef.LumpDefinitions.Add(); var shellDef = lumpDef.FaceShellDefinitions.Add(); var topFace = shellDef.FaceDefinitions.Add(topSurface, false); // TODO: What is this ID for? topFace.AssociativeID = 501; var topFaceLoop = topFace.EdgeLoopDefinitions.Add(); topFaceLoop.EdgeUseDefinitions.Add(edges[3], false); topFaceLoop.EdgeUseDefinitions.Add(edges[2], false); topFaceLoop.EdgeUseDefinitions.Add(edges[1], true); topFaceLoop.EdgeUseDefinitions.Add(edges[0], true); T1 = DateTime.Now; NameValueMap errors; var newBody = bodyDef.CreateTransientSurfaceBody(out errors); T2 = DateTime.Now; if (newBody == null) { throw new Exception("SurfaceBodyDefinition.CreateTransientSurfaceBody returned null"); } NonParametricBaseFeatureDefinition baseDef = features.NonParametricBaseFeatures.CreateDefinition(); ObjectCollection objColl = mApp.TransientObjects.CreateObjectCollection(); objColl.Add(newBody); baseDef.BRepEntities = objColl; baseDef.OutputType = BaseFeatureOutputTypeEnum.kSurfaceOutputType; NonParametricBaseFeature baseFeature = features.NonParametricBaseFeatures.AddByDefinition(baseDef); transaction.End(); } catch (Exception exc) { transaction.Abort(); } var Tfinal = DateTime.Now; var d01 = T1 - T0; var msg01 = string.Format("Time before CreateTransientSurfaceBody: {0} sec", d01.TotalSeconds); var d12 = T2 - T1; var msg12 = string.Format("CreateTransientSurfaceBody time: {0} sec", d12.TotalSeconds); var d2f = Tfinal - T2; var msg2f = string.Format("Time after CreateTransientSurfaceBody: {0} sec", d2f.TotalSeconds); MessageBox.Show(msg01 + "\n" + msg12 + "\n" + msg2f); }