public static void Draw(RenderContext11 renderContext, PositionColoredTextured[] points, int count, Texture11 texture, SharpDX.Direct3D.PrimitiveTopology primitiveType, float opacity = 1.0f) { if (VertexBuffer == null) { VertexBuffer = new Buffer(renderContext.Device, System.Runtime.InteropServices.Marshal.SizeOf(points[0]) * 2500, ResourceUsage.Dynamic, BindFlags.VertexBuffer, CpuAccessFlags.Write, ResourceOptionFlags.None, System.Runtime.InteropServices.Marshal.SizeOf(points[0])); VertexBufferBinding = new VertexBufferBinding(VertexBuffer, System.Runtime.InteropServices.Marshal.SizeOf((points[0])), 0); } renderContext.devContext.InputAssembler.PrimitiveTopology = primitiveType; renderContext.BlendMode = BlendMode.Alpha; renderContext.setRasterizerState(TriangleCullMode.Off); SharpDX.Matrix mat = (renderContext.World * renderContext.View * renderContext.Projection).Matrix11; mat.Transpose(); WarpOutputShader.MatWVP = mat; WarpOutputShader.Use(renderContext.devContext, texture != null, opacity); renderContext.SetVertexBuffer(VertexBufferBinding); DataBox box = renderContext.devContext.MapSubresource(VertexBuffer, 0, MapMode.WriteDiscard, MapFlags.None); Utilities.Write(box.DataPointer, points, 0, count); renderContext.devContext.UnmapSubresource(VertexBuffer, 0); if (texture != null) { renderContext.devContext.PixelShader.SetShaderResource(0, texture.ResourceView); } else { renderContext.devContext.PixelShader.SetShaderResource(0, null); } renderContext.devContext.Draw(count, 0); }
public static void Draw(RenderContext11 renderContext, PositionColoredTextured[] points, int count, Matrix mat, bool triangleStrip) { if (VertexBuffer == null) { VertexBuffer = new Buffer(renderContext.Device, System.Runtime.InteropServices.Marshal.SizeOf(points[0]) * 2500, ResourceUsage.Dynamic, BindFlags.VertexBuffer, CpuAccessFlags.Write, ResourceOptionFlags.None, System.Runtime.InteropServices.Marshal.SizeOf(points[0])); VertexBufferBinding = new VertexBufferBinding(VertexBuffer, System.Runtime.InteropServices.Marshal.SizeOf((points[0])), 0); } renderContext.devContext.InputAssembler.PrimitiveTopology = triangleStrip ? SharpDX.Direct3D.PrimitiveTopology.TriangleStrip : SharpDX.Direct3D.PrimitiveTopology.TriangleList; renderContext.BlendMode = BlendMode.Alpha; renderContext.setRasterizerState(TriangleCullMode.Off); mat.Transpose(); WarpOutputShader.MatWVP = mat; WarpOutputShader.Use(renderContext.devContext, false); renderContext.SetVertexBuffer(VertexBufferBinding); DataBox box = renderContext.devContext.MapSubresource(VertexBuffer, 0, MapMode.WriteDiscard, MapFlags.None); Utilities.Write(box.DataPointer, points, 0, count); renderContext.devContext.UnmapSubresource(VertexBuffer, 0); renderContext.devContext.PixelShader.SetShaderResource(0, null); renderContext.devContext.Draw(count, 0); }
/// <summary> /// Generates a list of triangles from an interior point (<paramref name="cx"/>;<paramref name="cy"/>) /// to each point of the source <paramref name="points"/>. The path must be closed and describe a simple polygon, /// where no connection between (cx; cy) and any path point crosses the border (this means, from (cx; cy), /// each path point must be reached directly). /// The generated triangles are in the same form as if we would have generated a triangle fan, /// but this method returns them in the form of a triangle list. /// </summary> /// <param name="points">The source points which enclose the shape to triangulate.</param> /// <param name="cx">X coordinate of an interior point of the <paramref name="points"/>.</param> /// <param name="cy">Y coordinate of an interior point of the <paramref name="points"/>.</param> /// <param name="zCoord">Z coordinate of the returned vertices.</param> /// <param name="verts">Returns a list of vertices describing a triangle list.</param> public static void FillPolygon_TriangleList(PointF[] points, float cx, float cy, float zCoord, out PositionColoredTextured[] verts) { verts = null; PointF[] pathPoints = AdjustPoints(points); int pointCount = pathPoints.Length; if (pointCount <= 2) return; if (pointCount == 3) { verts = new PositionColoredTextured[3]; verts[0].Position = new Vector3(pathPoints[0].X, pathPoints[0].Y, zCoord); verts[1].Position = new Vector3(pathPoints[1].X, pathPoints[1].Y, zCoord); verts[2].Position = new Vector3(pathPoints[2].X, pathPoints[2].Y, zCoord); return; } bool closed = pathPoints[0] == pathPoints[pointCount - 1]; if (closed) pointCount--; int verticeCount = pointCount * 3; verts = new PositionColoredTextured[verticeCount]; for (int i = 0; i < pointCount; i++) { int offset = i * 3; verts[offset].Position = new Vector3(cx, cy, zCoord); verts[offset + 1].Position = new Vector3(pathPoints[i].X, pathPoints[i].Y, zCoord); if (i + 1 < pointCount) verts[offset + 2].Position = new Vector3(pathPoints[i + 1].X, pathPoints[i + 1].Y, zCoord); else verts[offset + 2].Position = new Vector3(pathPoints[0].X, pathPoints[0].Y, zCoord); } }
public static void Flatten(PositionColoredTextured[][] subPathVerts, out PositionColoredTextured[] verts) { int numVertices = subPathVerts.Where(t => t != null).Sum(t => t.Length); if (numVertices == 0) { verts = null; return; } verts = new PositionColoredTextured[numVertices]; long offset = 0; foreach (PositionColoredTextured[] spv in subPathVerts) { if (spv == null) continue; long length = spv.Length; Array.Copy(spv, 0, verts, offset, length); offset += length; } }
/// <summary> /// Generates a triangle fan from an interior point (<paramref name="cx"/>;<paramref name="cy"/>) /// to each point of the source <paramref name="points"/>. The path must describe a simple polygon, /// where no connection between (cx; cy) and a path points crosses the border (this means, from (cx; cy), /// each path point must be reached directly). /// The path will be closed automatically, if it is not closed. /// The generated triangles are in the same form as if we would have generated a triangle fan, /// but this method returns them as triangle list. /// </summary> /// <param name="points">The source points which enclose the shape to triangulate.</param> /// <param name="cx">X coordinate of an interior point of the <paramref name="points"/>.</param> /// <param name="cy">Y coordinate of an interior point of the <paramref name="points"/>.</param> /// <param name="zCoord">Z coordinate of the returned vertices.</param> /// <param name="verts">Returns a list of vertices describing a triangle fan.</param> public static void FillPolygon_TriangleFan(PointF[] points, float cx, float cy, float zCoord, out PositionColoredTextured[] verts) { verts = null; PointF[] pathPoints = AdjustPoints(points); int pointCount = pathPoints.Length; if (pointCount <= 2) { return; } if (pointCount == 3) { verts = new PositionColoredTextured[3]; verts[0].Position = new Vector3(pathPoints[0].X, pathPoints[0].Y, zCoord); verts[1].Position = new Vector3(pathPoints[1].X, pathPoints[1].Y, zCoord); verts[2].Position = new Vector3(pathPoints[2].X, pathPoints[2].Y, zCoord); return; } bool close = pathPoints[0] != pathPoints[pointCount - 1]; int verticeCount = pointCount + (close ? 2 : 1); verts = new PositionColoredTextured[verticeCount]; verts[0].Position = new Vector3(cx, cy, zCoord); // First point is center point for (int i = 0; i < pointCount; i++) { // Set the outer fan points verts[i + 1].Position = new Vector3(pathPoints[i].X, pathPoints[i].Y, zCoord); } if (close) { // Last point is the first point to close the shape verts[verticeCount - 1].Position = new Vector3(pathPoints[0].X, pathPoints[0].Y, zCoord); } }
protected void PerformLayoutBorder(RectangleF innerBorderRect, RenderContext context) { // Setup border brush if (BorderBrush != null && BorderThickness > 0) { // TODO: Draw border with thickness BorderThickness - doesn't work yet, the drawn line is only one pixel thick using (GraphicsPath path = CreateBorderRectPath(innerBorderRect)) { using (GraphicsPathIterator gpi = new GraphicsPathIterator(path)) { PositionColoredTextured[][] subPathVerts = new PositionColoredTextured[gpi.SubpathCount][]; using (GraphicsPath subPath = new GraphicsPath()) { for (int i = 0; i < subPathVerts.Length; i++) { bool isClosed; gpi.NextSubpath(subPath, out isClosed); PointF[] pathPoints = subPath.PathPoints; PenLineJoin lineJoin = Math.Abs(CornerRadius) < DELTA_DOUBLE ? BorderLineJoin : PenLineJoin.Bevel; TriangulateHelper.TriangulateStroke_TriangleList(pathPoints, (float)BorderThickness, isClosed, 1, lineJoin, out subPathVerts[i]); } } PositionColoredTextured[] verts; GraphicsPathHelper.Flatten(subPathVerts, out verts); BorderBrush.SetupBrush(this, ref verts, context.ZOrder, true); PrimitiveBuffer.SetPrimitiveBuffer(ref _borderContext, ref verts, PrimitiveType.TriangleList); } } } else { PrimitiveBuffer.DisposePrimitiveBuffer(ref _borderContext); } }
private void CreateDonutGeometry() { float centerX = X; float centerY = Y; float radius = Width / 2; float circumference = (float)Math.PI * 2.0f * radius; int segments = (int)(circumference / 12) + 1; float radiansPerSegment = ((float)Math.PI * 2) / segments; if (points == null) { points = new PositionColoredTextured[segments * 2 + 2]; } for (int j = 0; j <= segments; j++) { int i = j * 2; points[i].Position = MakePosition(centerX, centerY, (float)(Math.Cos(j * radiansPerSegment) * (Width / 2)), (float)(Math.Sin(j * radiansPerSegment) * (Height / 2)), RotationAngle).Vector4; points[i].Tu = ((j) % 2); points[i].Tv = 0; points[i].Color = Color; points[i + 1].Position = MakePosition(centerX, centerY, (float)(Math.Cos(j * radiansPerSegment) * ((Width / 2) - 10)), (float)(Math.Sin(j * radiansPerSegment) * ((Height / 2) - 10)), RotationAngle).Vector4; points[i + 1].Tu = (j % 2); points[i + 1].Tv = 1; points[i + 1].Color = Color; } }
private void CreateOpenRectGeometry() { var centerX = X; var centerY = Y; var radius = Width / 2; var length = Width; var segments = (int)(length / 12f) + 1; var segmentsHigh = (int)(Height / 12f) + 1; var totalPoints = (((segments+1) * 2 )+((segmentsHigh+1)*2 ))*2; if (points == null) { points = new PositionColoredTextured[totalPoints]; } for (var j = 0; j <= segments; j++) { var i = j * 2; points[i].Position = MakePosition(centerX, centerY, (float)(j / (double)segments) * (Width) - (Width / 2), Height / 2, RotationAngle).Vector4; points[i].Tu = ((j) % 2); points[i].Tv = 0; points[i].Color = Color; points[i + 1].Position = MakePosition(centerX, centerY, (float)(j / (double)segments) * (Width) - (Width / 2), (Height / 2) - 12f, RotationAngle).Vector4; points[i + 1].Tu = (j % 2); points[i + 1].Tv = 1; points[i + 1].Color = Color; var k = (((segments+1) * 4)+((segmentsHigh+1)*2)-2)-i; points[k].Position = MakePosition(centerX, centerY, (float)(j / (double)segments) * (Width) - (Width / 2), -(Height / 2) + 12f, RotationAngle).Vector4; points[k].Tu = ((j) % 2); points[k].Tv = 0; points[k].Color = Color; points[k+1].Position = MakePosition(centerX, centerY, (float)(j / (double)segments) * (Width) - (Width / 2), -(Height / 2), RotationAngle).Vector4; points[k + 1].Tu = (j % 2); points[k + 1].Tv = 1; points[k + 1].Color = Color; } var offset = ((segments+1) * 2); for (var j = 0; j <= segmentsHigh; j++) { var top = ((segmentsHigh+1) * 2)+offset-2; var i = j * 2 ; points[top - i].Position = MakePosition(centerX, centerY, Width / 2, (float)((j / (double)segmentsHigh) * (Height) - (Height / 2)), RotationAngle).Vector4; points[top-i].Tu = ((j) % 2); points[top-i].Tv = 0; points[top-i].Color = Color; points[top - i + 1].Position = MakePosition(centerX, centerY, (Width / 2) - 12f, (float)((j / (double)segmentsHigh) * Height - ((Height / 2))), RotationAngle).Vector4; points[top-i + 1].Tu = (j % 2); points[top-i + 1].Tv = 1; points[top-i + 1].Color = Color; var k = i + ((segments + 1) * 4) + ((segmentsHigh + 1) * 2); points[k].Position = MakePosition(centerX, centerY, -(Width / 2) + 12, (float)((j / (double)segmentsHigh) * (Height) - (Height / 2)), RotationAngle).Vector4; points[k].Tu = ((j) % 2); points[k].Tv = 0; points[k].Color = Color; points[k + 1].Position = MakePosition(centerX, centerY, - (Width / 2), (float)((j / (double)segmentsHigh) * Height - ((Height / 2))), RotationAngle).Vector4; points[k + 1].Tu = (j % 2); points[k + 1].Tv = 1; points[k + 1].Color = Color; } }
private void CreateArrowGeometry() { if (points == null) { points = new PositionColoredTextured[9]; } points[0].Position = MakePosition(X, Y, -Width / 2, -Height / 4, RotationAngle).Vector4; points[0].Tu = 0; points[0].Tv = 0; points[0].Color = Color; points[1].Position = MakePosition(X, Y, Width / 4, -Height / 4, RotationAngle).Vector4; points[1].Tu = 1; points[1].Tv = 0; points[1].Color = Color; points[2].Position = MakePosition(X, Y, -Width / 2, Height / 4, RotationAngle).Vector4; points[2].Tu = 0; points[2].Tv = 1; points[2].Color = Color; points[3].Position = MakePosition(X, Y, Width / 4, -Height / 4, RotationAngle).Vector4; points[3].Tu = 1; points[3].Tv = 0; points[3].Color = Color; points[4].Position = MakePosition(X, Y, -Width / 2, Height / 4, RotationAngle).Vector4; points[4].Tu = 0; points[4].Tv = 1; points[4].Color = Color; points[5].Position = MakePosition(X, Y, Width / 4, Height / 4, RotationAngle).Vector4; points[5].Tu = 1; points[5].Tv = 1; points[5].Color = Color; // Point points[6].Position = MakePosition(X, Y, Width / 4, -Height / 2, RotationAngle).Vector4; points[6].Tu = 1; points[6].Tv = 1; points[6].Color = Color; points[7].Position = MakePosition(X, Y, Width / 2, 0, RotationAngle).Vector4; points[7].Tu = 1; points[7].Tv = .5f; points[7].Color = Color; points[8].Position = MakePosition(X, Y, Width / 4, Height / 2, RotationAngle).Vector4; points[8].Tu = 1; points[8].Tv = 1; points[8].Color = Color; TriangleStrip = false; }
public string ToWellKnownText() { if (shapefile == null) { return null; } var sb = new StringBuilder(); // Make Header sb.Append("Geography"); if (shapefile.Table != null) { foreach (DataColumn col in shapefile.Table.Columns) { sb.Append("\t"); sb.Append(col.ColumnName); } } sb.AppendLine(); var firstItem = true; var firstShape = true; var north = true; double offsetX = 0; double offsetY = 0; double centralMeridian = 0; double mapScale = 0; double standardParallel = 70; if (shapefile.Projection == ShapeFile.Projections.PolarStereo) { north = shapefile.FileHeader.ProjectionInfo.Name.ToLower().Contains("north"); standardParallel = shapefile.FileHeader.ProjectionInfo.GetParameter("standard_parallel_1"); centralMeridian = shapefile.FileHeader.ProjectionInfo.GetParameter("central_meridian"); mapScale = shapefile.FileHeader.ProjectionInfo.GetParameter("scale_factor"); offsetY = shapefile.FileHeader.ProjectionInfo.GetParameter("false_easting"); offsetX = shapefile.FileHeader.ProjectionInfo.GetParameter("false_northing"); } var color = Color.ToArgb(); var count = 360; for (var i = 0; i < shapefile.Shapes.Count; i++) { if (shapefile.Shapes[i].GetType() == typeof(Polygon)) { firstShape = true; firstItem = true; sb.Append("Polygon ("); var p = (Polygon)shapefile.Shapes[i]; for (var z = 0; z < p.Rings.Length; z++) { if (firstShape) { firstShape = false; } else { sb.Append(","); } sb.Append("("); count = (p.Rings[z].Points.Length); // content from DBF var dr = p.Rings[z].Attributes; firstItem = true; for (var k = 0; k < p.Rings[z].Points.Length; k++) { // 2D Point coordinates. 3d also supported which would add a Z. There's also an optional measure (M) that can be used. var Xcoord = p.Rings[z].Points[k].X; var Ycoord = p.Rings[z].Points[k].Y; if (firstItem) { firstItem = false; } else { sb.Append(","); } // sb.Append(Xcoord.ToString("F5") + " " + Ycoord.ToString("F5")); sb.Append(Xcoord + " " + Ycoord); } sb.Append(")"); } sb.Append(")"); AddTableRow(sb, shapefile.Shapes[i].Attributes); sb.AppendLine(); } else if (shapefile.Shapes[i].GetType() == typeof(PolyLine)) { var p = (PolyLine)shapefile.Shapes[i]; for (var z = 0; z < p.Lines.Length; z++) { firstShape = true; firstItem = true; sb.Append("LineString ("); count = (p.Lines[z].Points.Length); var points = new PositionColoredTextured[(count)]; firstItem = true; for (var k = 0; k < p.Lines[z].Points.Length; k++) { //if (firstShape) //{ // firstShape = false; //} //else //{ // sb.Append(","); //} // 2D Point coordinates. 3d also supported which would add a Z. There's also an optional measure (M) that can be used. var Xcoord = p.Lines[z].Points[k].X; var Ycoord = p.Lines[z].Points[k].Y; if (firstItem) { firstItem = false; } else { sb.Append(","); } sb.Append(Xcoord + " " + Ycoord); } sb.Append(")"); AddTableRow(sb, shapefile.Shapes[i].Attributes); sb.AppendLine(); } } else if (shapefile.Shapes[i].GetType() == typeof(PolyLineZ)) { var p = (PolyLineZ)shapefile.Shapes[i]; for (var z = 0; z < p.Lines.Length; z++) { firstShape = true; firstItem = true; sb.Append("LineString ("); count = (p.Lines[z].Points.Length); var points = new PositionColoredTextured[(count)]; firstItem = true; for (var k = 0; k < p.Lines[z].Points.Length; k++) { //if (firstShape) //{ // firstShape = false; //} //else //{ // sb.Append(","); //} // 2D Point coordinates. 3d also supported which would add a Z. There's also an optional measure (M) that can be used. var Xcoord = p.Lines[z].Points[k].X; var Ycoord = p.Lines[z].Points[k].Y; var Zcoord = p.Lines[z].Points[k].Z; if (firstItem) { firstItem = false; } else { sb.Append(","); } sb.Append(Xcoord + " " + Ycoord + " " + Zcoord); } sb.Append(")"); AddTableRow(sb, shapefile.Shapes[i].Attributes); sb.AppendLine(); } } else if (shapefile.Shapes[i].GetType() == typeof(Point)) { var p = (Point)shapefile.Shapes[i]; // 2D Point coordinates. 3d also supported which would add a Z. There's also an optional measure (M) that can be used. var Xcoord = p.X; var Ycoord = p.Y; sb.Append(string.Format("Point ({0} {1})")); AddTableRow(sb, shapefile.Shapes[i].Attributes); sb.AppendLine(); } } return sb.ToString(); }
/// <summary> /// Generates the vertices of a thickened line strip. /// </summary> /// <param name="points">Points of the line strip</param> /// <param name="thickness">Thickness of the line</param> /// <param name="close">Whether to connect the last point back to the first</param> /// <param name="widthMode">How to place the weight of the line relative to it</param> /// <param name="zCoord">Z coordinate of the returned vertices.</param> /// <param name="verts">Generated vertices.</param> public static void CalculateLinePoints(PointF[] points, float thickness, bool close, WidthMode widthMode, float zCoord, out PositionColoredTextured[] verts) { PointF[] pathPoints = AdjustPoints(points); verts = null; if (pathPoints.Length < 3) { if (close) return; if (pathPoints.Length < 2) return; } int count = pathPoints.Length; if (pathPoints[count - 2] == pathPoints[count - 1]) count--; Vector2[] vPoints = new Vector2[count]; for (int i = 0; i < count; ++i) vPoints[i] = new Vector2(pathPoints[i].X, pathPoints[i].Y); Vector2 innerDistance = new Vector2(0, 0); switch (widthMode) { case WidthMode.Centered: //innerDistance =thickness / 2; innerDistance = new Vector2(thickness / 2, thickness / 2); break; case WidthMode.LeftHanded: //innerDistance = -thickness; innerDistance = new Vector2(-thickness, -thickness); break; case WidthMode.RightHanded: //innerDistance = thickness; innerDistance = new Vector2(thickness, thickness); break; } Vector2[] outPoints = new Vector2[(vPoints.Length + (close ? 1 : 0)) * 2]; float slope, intercept; //Get the endpoints if (close) { //Get the overlap points int lastIndex = outPoints.Length - 4; outPoints[lastIndex] = InnerPoint(innerDistance, vPoints[vPoints.Length - 2], vPoints[vPoints.Length - 1], vPoints[0], out slope, out intercept); outPoints[0] = InnerPoint(innerDistance, ref slope, ref intercept, outPoints[lastIndex], vPoints[0], vPoints[1]); } else { //Take endpoints based on the end segments' normals alone outPoints[0] = Vector2.Multiply(innerDistance, GetNormal(vPoints[1] - vPoints[0])); outPoints[0] = vPoints[0] + outPoints[0]; //outPoints[0] = points[0] + innerDistance * normal(points[1] - points[0]); Vector2 norm = Vector2.Multiply(innerDistance, GetNormal(vPoints[vPoints.Length - 1] - vPoints[vPoints.Length - 2])); //DEBUG outPoints[outPoints.Length - 2] = vPoints[vPoints.Length - 1] + norm; //Get the slope and intercept of the first segment to feed into the middle loop slope = VectorSlope(vPoints[1] - vPoints[0]); intercept = LineIntercept(outPoints[0], slope); } //Get the middle points for (int i = 1; i < vPoints.Length - 1; i++) outPoints[2 * i] = InnerPoint(innerDistance, ref slope, ref intercept, outPoints[2 * (i - 1)], vPoints[i], vPoints[i + 1]); //Derive the outer points from the inner points if (widthMode == WidthMode.Centered) for (int i = 0; i < vPoints.Length; i++) outPoints[2 * i + 1] = 2 * vPoints[i] - outPoints[2 * i]; else for (int i = 0; i < vPoints.Length; i++) outPoints[2 * i + 1] = vPoints[i]; //Closed strips must repeat the first two points if (close) { outPoints[outPoints.Length - 2] = outPoints[0]; outPoints[outPoints.Length - 1] = outPoints[1]; } int verticeCount = outPoints.Length; verts = new PositionColoredTextured[verticeCount]; for (int i = 0; i < verticeCount; ++i) verts[i].Position = new Vector3(outPoints[i].X, outPoints[i].Y, zCoord); }
private void CreateStarGeometry() { float centerX = X; float centerY = Y; float radius = Width / 2; float radiansPerSegment = ((float)Math.PI * 2) / 5; if (points == null) { points = new PositionColoredTextured[12]; } if (pnts == null) { pnts = new PositionColoredTextured[10]; } for (int i = 0; i < 5; i++) { double rads = i * radiansPerSegment - (Math.PI/2) ; pnts[i].Position = MakePosition(centerX, centerY, (float)(Math.Cos(rads) * (Width / 2)), (float)(Math.Sin(rads) * (Height / 2)), RotationAngle).Vector4; pnts[i].Tu = 0; pnts[i].Tv = 0; pnts[i].Color = Color; } for (int i = 5; i < 10; i++) { double rads = i * radiansPerSegment + (radiansPerSegment / 2) - (Math.PI/2); pnts[i].Position = MakePosition(centerX, centerY, (float)(Math.Cos(rads) * (Width / 5.3)), (float)(Math.Sin(rads) * (Height / 5.3)), RotationAngle).Vector4; pnts[i].Tu = 0; pnts[i].Tv = 0; pnts[i].Color = Color; } points[0] = pnts[0]; points[1] = pnts[5]; points[2] = pnts[9]; points[3] = pnts[1]; points[4] = pnts[7]; points[5] = pnts[4]; points[6] = pnts[6]; points[7] = pnts[2]; points[8] = pnts[7]; points[9] = pnts[7]; points[10] = pnts[3]; points[11] = pnts[8]; TriangleStrip = false; }
public override void InitiaizeGeometry() { int frameCount = frames; if (!String.IsNullOrEmpty(frameSequence)) { frameCount = framesList.Count; } if (playing) { // todo allow play backwards loop to point. TimeSpan ts = SpaceTimeController.MetaNow - timeStart; switch (loopType) { case LoopTypes.Loop: currentFrame = (int)((ts.TotalSeconds * 24.0) % frameCount) +startFrame; break; case LoopTypes.UpDown: currentFrame = Math.Abs((int)((ts.TotalSeconds * 24.0 + frameCount) % (frameCount * 2 - 1)) - (frameCount - 1)) + startFrame; break; case LoopTypes.Down: currentFrame = Math.Max(0, frameCount - (int)((ts.TotalSeconds * 24.0) % frameCount)) + startFrame; break; case LoopTypes.UpDownOnce: int temp = (int)Math.Min(ts.TotalSeconds * 24.0,frameCount *2 +1) + frameCount; currentFrame = Math.Abs((int)((temp) % (frameCount * 2 - 1)) - (frameCount - 1)) + startFrame; break; case LoopTypes.Once: currentFrame = Math.Min(frameCount - 1, (int)((ts.TotalSeconds * 24.0))); break; case LoopTypes.Begin: currentFrame = startFrame; break; case LoopTypes.End: currentFrame = (frameCount - 1) + startFrame; break; default: currentFrame = startFrame; break; } } if (!String.IsNullOrEmpty(frameSequence)) { if (currentFrame < framesList.Count && currentFrame > -1) { currentFrame = framesList[currentFrame]; } else { currentFrame = 0; } } currentRotation = 0; if (points == null) { points = new PositionColoredTextured[4]; } float cellHeight = 1f / framesY; float cellWidth = 1f / framesX; int indexX = currentFrame % framesX; int indexY = (int)(currentFrame / framesX); points[0].Position = MakePosition(X, Y, -(Width / 2), -(Height / 2), RotationAngle).Vector4; points[0].Tu = indexX * cellWidth; points[0].Tv = indexY * cellHeight; points[0].Color = Color; points[1].Position = MakePosition(X, Y, (Width / 2), -(Height / 2), RotationAngle).Vector4; points[1].Tu = indexX * cellWidth + cellWidth; points[1].Tv = indexY * cellHeight; points[1].Color = Color; points[2].Position = MakePosition(X, Y, -(Width / 2), (Height / 2), RotationAngle).Vector4; points[2].Tu = indexX * cellWidth; points[2].Tv = indexY * cellHeight + cellHeight; points[2].Color = Color; points[3].Position = MakePosition(X, Y, (Width / 2), (Height / 2), RotationAngle).Vector4; points[3].Tu = indexX * cellWidth + cellWidth; points[3].Tv = indexY * cellHeight + cellHeight; points[3].Color = Color; }
/// <summary> /// Creates a <see cref="PrimitiveType.TriangleList"/> of vertices which cover the interior of the /// specified <paramref name="points"/>. The path must be closed and describe a simple polygon. /// </summary> /// <param name="points">Points describing the border of a simple polygon.</param> /// <param name="zCoord">Z coordinate of the created vertices.</param> /// <param name="verts">Returns a <see cref="PrimitiveType.TriangleList"/> of vertices.</param> public static void Triangulate(PointF[] points, float zCoord, out PositionColoredTextured[] verts) { PointF[] pathPoints = AdjustPoints(points); if (pathPoints.Length < 3) { verts = null; return; } if (pathPoints.Length == 3) { verts = new PositionColoredTextured[3]; verts[0].Position = new Vector3(pathPoints[0].X, pathPoints[0].Y, zCoord); verts[1].Position = new Vector3(pathPoints[1].X, pathPoints[1].Y, zCoord); verts[2].Position = new Vector3(pathPoints[2].X, pathPoints[2].Y, zCoord); return; } ICollection<CPolygon> polygons; try { // Triangulation can fail (i.e. polygon is self-intersecting) polygons = new List<CPolygon>(new CPolygon(pathPoints).Triangulate()); } catch (Exception) { verts = null; return; } verts = new PositionColoredTextured[polygons.Count * 3]; int offset = 0; foreach (CPolygon triangle in polygons) { verts[offset++].Position = new Vector3(triangle[0].X, triangle[0].Y, zCoord); verts[offset++].Position = new Vector3(triangle[1].X, triangle[1].Y, zCoord); verts[offset++].Position = new Vector3(triangle[2].X, triangle[2].Y, zCoord); } }
public string ToWellKnownText() { if (shapefile == null) { return(null); } StringBuilder sb = new StringBuilder(); // Make Header sb.Append("Geography"); if (shapefile.Table != null) { foreach (DataColumn col in shapefile.Table.Columns) { sb.Append("\t"); sb.Append(col.ColumnName); } } sb.AppendLine(); bool firstItem = true; bool firstShape = true; bool north = true; double offsetX = 0; double offsetY = 0; double centralMeridian = 0; double mapScale = 0; double standardParallel = 70; if (shapefile.Projection == ShapeFile.Projections.PolarStereo) { north = shapefile.FileHeader.ProjectionInfo.Name.ToLower().Contains("north"); standardParallel = shapefile.FileHeader.ProjectionInfo.GetParameter("standard_parallel_1"); centralMeridian = shapefile.FileHeader.ProjectionInfo.GetParameter("central_meridian"); mapScale = shapefile.FileHeader.ProjectionInfo.GetParameter("scale_factor"); offsetY = shapefile.FileHeader.ProjectionInfo.GetParameter("false_easting"); offsetX = shapefile.FileHeader.ProjectionInfo.GetParameter("false_northing"); } int color = Color.ToArgb(); int count = 360; for (int i = 0; i < shapefile.Shapes.Count; i++) { if (shapefile.Shapes[i].GetType() == typeof(Polygon)) { firstShape = true; firstItem = true; sb.Append("Polygon ("); Polygon p = (Polygon)shapefile.Shapes[i]; for (int z = 0; z < p.Rings.Length; z++) { if (firstShape) { firstShape = false; } else { sb.Append(","); } sb.Append("("); count = (p.Rings[z].Points.Length); // content from DBF DataRow dr = p.Rings[z].Attributes; firstItem = true; for (int k = 0; k < p.Rings[z].Points.Length; k++) { // 2D Point coordinates. 3d also supported which would add a Z. There's also an optional measure (M) that can be used. double Xcoord = p.Rings[z].Points[k].X; double Ycoord = p.Rings[z].Points[k].Y; if (firstItem) { firstItem = false; } else { sb.Append(","); } // sb.Append(Xcoord.ToString("F5") + " " + Ycoord.ToString("F5")); sb.Append(Xcoord.ToString() + " " + Ycoord.ToString()); } sb.Append(")"); } sb.Append(")"); AddTableRow(sb, shapefile.Shapes[i].Attributes); sb.AppendLine(); } else if (shapefile.Shapes[i].GetType() == typeof(PolyLine)) { PolyLine p = (PolyLine)shapefile.Shapes[i]; for (int z = 0; z < p.Lines.Length; z++) { firstShape = true; firstItem = true; sb.Append("LineString ("); count = (p.Lines[z].Points.Length); PositionColoredTextured[] points = new PositionColoredTextured[(count)]; firstItem = true; for (int k = 0; k < p.Lines[z].Points.Length; k++) { //if (firstShape) //{ // firstShape = false; //} //else //{ // sb.Append(","); //} // 2D Point coordinates. 3d also supported which would add a Z. There's also an optional measure (M) that can be used. double Xcoord = p.Lines[z].Points[k].X; double Ycoord = p.Lines[z].Points[k].Y; if (firstItem) { firstItem = false; } else { sb.Append(","); } sb.Append(Xcoord.ToString() + " " + Ycoord.ToString()); } sb.Append(")"); AddTableRow(sb, shapefile.Shapes[i].Attributes); sb.AppendLine(); } } else if (shapefile.Shapes[i].GetType() == typeof(PolyLineZ)) { PolyLineZ p = (PolyLineZ)shapefile.Shapes[i]; for (int z = 0; z < p.Lines.Length; z++) { firstShape = true; firstItem = true; sb.Append("LineString ("); count = (p.Lines[z].Points.Length); PositionColoredTextured[] points = new PositionColoredTextured[(count)]; firstItem = true; for (int k = 0; k < p.Lines[z].Points.Length; k++) { //if (firstShape) //{ // firstShape = false; //} //else //{ // sb.Append(","); //} // 2D Point coordinates. 3d also supported which would add a Z. There's also an optional measure (M) that can be used. double Xcoord = p.Lines[z].Points[k].X; double Ycoord = p.Lines[z].Points[k].Y; double Zcoord = p.Lines[z].Points[k].Z; if (firstItem) { firstItem = false; } else { sb.Append(","); } sb.Append(Xcoord.ToString() + " " + Ycoord.ToString() + " " + Zcoord.ToString()); } sb.Append(")"); AddTableRow(sb, shapefile.Shapes[i].Attributes); sb.AppendLine(); } } else if (shapefile.Shapes[i].GetType() == typeof(ShapefileTools.Point)) { ShapefileTools.Point p = (ShapefileTools.Point)shapefile.Shapes[i]; // 2D Point coordinates. 3d also supported which would add a Z. There's also an optional measure (M) that can be used. double Xcoord = p.X; double Ycoord = p.Y; sb.Append(string.Format("Point ({0} {1})")); AddTableRow(sb, shapefile.Shapes[i].Attributes); sb.AppendLine(); } } return(sb.ToString()); }
public void AddGlyphPoints(List<PositionColoredTextured> pointList, SizeF size, RectangleF position, RectangleF uv) { PositionColoredTextured[] points = new PositionColoredTextured[6]; Vector3d left = Vector3d.Cross(center, up); Vector3d right = Vector3d.Cross(up, center); left.Normalize(); right.Normalize(); up.Normalize(); Vector3d upTan = Vector3d.Cross(center, right); upTan.Normalize(); if (alignment == Alignment.Center) { left.Multiply(width - position.Left * 2); right.Multiply(width - ((width * 2) - position.Right * 2)); } else if (alignment == Alignment.Left) { left.Multiply(-position.Left * 2); right.Multiply(position.Right * 2); } Vector3d top = upTan; Vector3d bottom = -upTan; top.Multiply(height-position.Top*2); bottom.Multiply(height-((height*2)-position.Bottom*2)); Vector3d ul = center; ul.Add(top); if (sky) { ul.Add(left); } else { ul.Subtract(left); } Vector3d ur = center; ur.Add(top); if (sky) { ur.Add(right); } else { ur.Subtract(right); } Vector3d ll = center; if (sky) { ll.Add(left); } else { ll.Subtract(left); } ll.Add(bottom); Vector3d lr = center; if (sky) { lr.Add(right); } else { lr.Subtract(right); } lr.Add(bottom); points[0].Pos3d = ul; points[0].Tu = uv.Left; points[0].Tv = uv.Top; points[0].Color = Color; points[2].Tu = uv.Left; points[2].Tv = uv.Bottom; points[2].Pos3d = ll; points[2].Color = Color; points[1].Tu = uv.Right; points[1].Tv = uv.Top; points[1].Pos3d = ur; points[1].Color = Color; points[3].Tu = uv.Right; points[3].Tv = uv.Bottom; points[3].Pos3d = lr; points[3].Color = Color; points[5].Tu = uv.Right; points[5].Tv = uv.Top; points[5].Pos3d = ur; points[5].Color = Color; points[4].Tu = uv.Left; points[4].Tv = uv.Bottom; points[4].Pos3d = ll; points[4].Color = Color; if (Rotation != 0 || Tilt != 0 || Bank != 0) { if (!matInit) { Matrix3d lookAt = Matrix3d.LookAtLH(center, new Vector3d(0, 0, 0), up); Matrix3d lookAtInv = lookAt; lookAtInv.Invert(); rtbMat = lookAt * Matrix3d.RotationZ(-Rotation / 180 * Math.PI) * Matrix3d.RotationX(-Tilt / 180 * Math.PI) * Matrix3d.RotationY(-Bank / 180 * Math.PI) * lookAtInv; //todo make this true after debug matInit = false; } for (int i = 0; i < 6; i++) { Vector3d pos = points[i].Pos3d; pos.TransformCoordinate(rtbMat); points[i].Pos3d = pos; } } pointList.AddRange(points); }
public static List <MeshGroup> FromFbx(string filePath) { List <MeshGroup> group = new List <MeshGroup>(); const float Scale = 1.0f; var assimp = new Assimp.AssimpContext(); var scene = assimp.ImportFile(filePath, Assimp.PostProcessSteps.PreTransformVertices); var baseFilePath = Path.GetDirectoryName(filePath); TexList = new List <string>(); TextureData = new List <Tm2>(); foreach (Assimp.Material mat in scene.Materials) { TexList.Add(Path.GetFileName(mat.TextureDiffuse.FilePath)); Stream str = File.OpenRead(TexList[TexList.Count - 1]); PngImage png = new PngImage(str); Tm2 tmImage = Tm2.Create(png); TextureData.Add(tmImage); } for (int i = 0; i < scene.RootNode.ChildCount; i++) { Node child = scene.RootNode.Children[i]; MeshGroup currentMeshGroup = new MeshGroup(); currentMeshGroup.MeshDescriptors = new List <MeshDescriptor>(); // Get meshes by ID. foreach (int j in child.MeshIndices) { MeshDescriptor meshDescriptor = new MeshDescriptor(); Mesh x = scene.Meshes[j]; var vertices = new PositionColoredTextured[x.Vertices.Count]; for (var k = 0; k < vertices.Length; k++) { vertices[k].X = x.Vertices[k].X * Scale; vertices[k].Y = x.Vertices[k].Y * Scale; vertices[k].Z = x.Vertices[k].Z * Scale; vertices[k].Tu = x.TextureCoordinateChannels[0][k].X; vertices[k].Tv = 1.0f - x.TextureCoordinateChannels[0][k].Y; vertices[k].R = x.VertexColorChannels[0][i].R; vertices[k].G = x.VertexColorChannels[0][i].G; vertices[k].B = x.VertexColorChannels[0][i].B; vertices[k].A = x.VertexColorChannels[0][i].A; } meshDescriptor.Vertices = vertices; meshDescriptor.Indices = x.GetIndices(); meshDescriptor.IsOpaque = false; meshDescriptor.TextureIndex = x.MaterialIndex; currentMeshGroup.MeshDescriptors.Add(meshDescriptor); } group.Add(currentMeshGroup); } return(group); }
protected override void DoPerformLayout(RenderContext context) { base.DoPerformLayout(context); // Setup brushes if (Fill != null || ((Stroke != null && StrokeThickness > 0))) { using (GraphicsPath path = CalculateTransformedPath(_innerRect)) { if (Fill != null && !_fillDisabled) { using (GraphicsPathIterator gpi = new GraphicsPathIterator(path)) { PositionColoredTextured[][] subPathVerts = new PositionColoredTextured[gpi.SubpathCount][]; using (GraphicsPath subPath = new GraphicsPath()) { for (int i = 0; i < subPathVerts.Length; i++) { bool isClosed; gpi.NextSubpath(subPath, out isClosed); PointF[] pathPoints = subPath.PathPoints; TriangulateHelper.Triangulate(pathPoints, 1, out subPathVerts[i]); if (subPathVerts[i] == null) { ServiceRegistration.Get <ILogger>().Warn("Failed to triangulate Path \"{0}\"!", Name); } } } PositionColoredTextured[] verts; GraphicsPathHelper.Flatten(subPathVerts, out verts); if (verts != null) { Fill.SetupBrush(this, ref verts, context.ZOrder, true); PrimitiveBuffer.SetPrimitiveBuffer(ref _fillContext, ref verts, PrimitiveType.TriangleList); } } } else { PrimitiveBuffer.DisposePrimitiveBuffer(ref _fillContext); } if (Stroke != null && StrokeThickness > 0) { using (GraphicsPathIterator gpi = new GraphicsPathIterator(path)) { PositionColoredTextured[][] subPathVerts = new PositionColoredTextured[gpi.SubpathCount][]; using (GraphicsPath subPath = new GraphicsPath()) { for (int i = 0; i < subPathVerts.Length; i++) { bool isClosed; gpi.NextSubpath(subPath, out isClosed); PointF[] pathPoints = subPath.PathPoints; TriangulateHelper.TriangulateStroke_TriangleList(pathPoints, (float)StrokeThickness, isClosed, 1, StrokeLineJoin, out subPathVerts[i]); } } PositionColoredTextured[] verts; GraphicsPathHelper.Flatten(subPathVerts, out verts); if (verts != null) { Stroke.SetupBrush(this, ref verts, context.ZOrder, true); PrimitiveBuffer.SetPrimitiveBuffer(ref _strokeContext, ref verts, PrimitiveType.TriangleList); } } } else { PrimitiveBuffer.DisposePrimitiveBuffer(ref _strokeContext); } } } }
public static void DrawForScreen(RenderContext11 renderContext, PositionColoredTextured[] points, int count, Texture11 texture, PrimitiveTopology primitiveType) { if (VertexBuffer == null) { VertexBuffer = new Buffer(renderContext.Device, Marshal.SizeOf(points[0]) * 2500, ResourceUsage.Dynamic, BindFlags.VertexBuffer, CpuAccessFlags.Write, ResourceOptionFlags.None, Marshal.SizeOf(points[0])); VertexBufferBinding = new VertexBufferBinding(VertexBuffer, Marshal.SizeOf((points[0])), 0); } renderContext.devContext.InputAssembler.PrimitiveTopology = primitiveType; renderContext.BlendMode = BlendMode.Alpha; renderContext.setRasterizerState(TriangleCullMode.Off); var mat = Matrix.Translation(-renderContext.ViewPort.Width / 2, -renderContext.ViewPort.Height / 2, 0) * Matrix.Scaling(1f, -1f, 1f) * Matrix.OrthoLH(renderContext.ViewPort.Width, renderContext.ViewPort.Height, 1, -1); mat.Transpose(); WarpOutputShader.MatWVP = mat; WarpOutputShader.Use(renderContext.devContext, texture != null); renderContext.SetVertexBuffer(VertexBufferBinding); var box = renderContext.devContext.MapSubresource(VertexBuffer, 0, MapMode.WriteDiscard, MapFlags.None); Utilities.Write(box.DataPointer, points, 0, count); renderContext.devContext.UnmapSubresource(VertexBuffer, 0); if (texture != null) { renderContext.devContext.PixelShader.SetShaderResource(0, texture.ResourceView); } else { renderContext.devContext.PixelShader.SetShaderResource(0, null); } renderContext.devContext.Draw(count, 0); }
public void AddGlyphPoints(List <PositionColoredTextured> pointList, SizeF size, RectangleF position, RectangleF uv) { PositionColoredTextured[] points = new PositionColoredTextured[6]; Vector3d left = Vector3d.Cross(center, up); Vector3d right = Vector3d.Cross(up, center); left.Normalize(); right.Normalize(); up.Normalize(); Vector3d upTan = Vector3d.Cross(center, right); upTan.Normalize(); if (alignment == Alignment.Center) { left.Multiply(width - position.Left * 2); right.Multiply(width - ((width * 2) - position.Right * 2)); } else if (alignment == Alignment.Left) { left.Multiply(-position.Left * 2); right.Multiply(position.Right * 2); } Vector3d top = upTan; Vector3d bottom = -upTan; top.Multiply(height - position.Top * 2); bottom.Multiply(height - ((height * 2) - position.Bottom * 2)); Vector3d ul = center; ul.Add(top); if (sky) { ul.Add(left); } else { ul.Subtract(left); } Vector3d ur = center; ur.Add(top); if (sky) { ur.Add(right); } else { ur.Subtract(right); } Vector3d ll = center; if (sky) { ll.Add(left); } else { ll.Subtract(left); } ll.Add(bottom); Vector3d lr = center; if (sky) { lr.Add(right); } else { lr.Subtract(right); } lr.Add(bottom); points[0].Pos3d = ul; points[0].Tu = uv.Left; points[0].Tv = uv.Top; points[0].Color = Color; points[2].Tu = uv.Left; points[2].Tv = uv.Bottom; points[2].Pos3d = ll; points[2].Color = Color; points[1].Tu = uv.Right; points[1].Tv = uv.Top; points[1].Pos3d = ur; points[1].Color = Color; points[3].Tu = uv.Right; points[3].Tv = uv.Bottom; points[3].Pos3d = lr; points[3].Color = Color; points[5].Tu = uv.Right; points[5].Tv = uv.Top; points[5].Pos3d = ur; points[5].Color = Color; points[4].Tu = uv.Left; points[4].Tv = uv.Bottom; points[4].Pos3d = ll; points[4].Color = Color; if (Rotation != 0 || Tilt != 0 || Bank != 0) { if (!matInit) { Matrix3d lookAt = Matrix3d.LookAtLH(center, new Vector3d(0, 0, 0), up); Matrix3d lookAtInv = lookAt; lookAtInv.Invert(); rtbMat = lookAt * Matrix3d.RotationZ(-Rotation / 180 * Math.PI) * Matrix3d.RotationX(-Tilt / 180 * Math.PI) * Matrix3d.RotationY(-Bank / 180 * Math.PI) * lookAtInv; //todo make this true after debug matInit = false; } for (int i = 0; i < 6; i++) { Vector3d pos = points[i].Pos3d; pos.TransformCoordinate(rtbMat); points[i].Pos3d = pos; } } pointList.AddRange(points); }
private void CreateLineGeometry() { float centerX = X; float centerY = Y; float radius = Width / 2; //float length = (float)Math.Sqrt(Width * Width + Height * Height); float length = (float)Width; int segments = (int)(length / 12f) + 1; float radiansPerSegment = ((float)Math.PI * 2) / segments; if (points == null) { points = new PositionColoredTextured[segments * 2 + 2]; } for (int j = 0; j <= segments; j++) { int i = j * 2; points[i].Position = MakePosition(X, Y, (float)(((double)j / (double)segments) * (Width) - (Width / 2)), 6f, RotationAngle).Vector4; points[i].Tu = ((j) % 2); points[i].Tv = 0; points[i].Color = Color; points[i + 1].Position = MakePosition(X, Y, (float)(((double)j / (double)segments) * (Width) - (Width / 2)), -6f, RotationAngle).Vector4; points[i + 1].Tu = (j % 2); points[i + 1].Tv = 1; points[i + 1].Color = Color; } }
/// <summary> /// Generates a triangle fan from an interior point (<paramref name="cx"/>;<paramref name="cy"/>) /// to each point of the source <paramref name="points"/>. The path must describe a simple polygon, /// where no connection between (cx; cy) and a path points crosses the border (this means, from (cx; cy), /// each path point must be reached directly). /// The path will be closed automatically, if it is not closed. /// The generated triangles are in the same form as if we would have generated a triangle fan, /// but this method returns them as triangle list. /// </summary> /// <param name="points">The source points which enclose the shape to triangulate.</param> /// <param name="cx">X coordinate of an interior point of the <paramref name="points"/>.</param> /// <param name="cy">Y coordinate of an interior point of the <paramref name="points"/>.</param> /// <param name="zCoord">Z coordinate of the returned vertices.</param> /// <param name="verts">Returns a list of vertices describing a triangle fan.</param> public static void FillPolygon_TriangleFan(PointF[] points, float cx, float cy, float zCoord, out PositionColoredTextured[] verts) { verts = null; PointF[] pathPoints = AdjustPoints(points); int pointCount = pathPoints.Length; if (pointCount <= 2) return; if (pointCount == 3) { verts = new PositionColoredTextured[3]; verts[0].Position = new Vector3(pathPoints[0].X, pathPoints[0].Y, zCoord); verts[1].Position = new Vector3(pathPoints[1].X, pathPoints[1].Y, zCoord); verts[2].Position = new Vector3(pathPoints[2].X, pathPoints[2].Y, zCoord); return; } bool close = pathPoints[0] != pathPoints[pointCount - 1]; int verticeCount = pointCount + (close ? 2 : 1); verts = new PositionColoredTextured[verticeCount]; verts[0].Position = new Vector3(cx, cy, zCoord); // First point is center point for (int i = 0; i < pointCount; i++) // Set the outer fan points verts[i + 1].Position = new Vector3(pathPoints[i].X, pathPoints[i].Y, zCoord); if (close) // Last point is the first point to close the shape verts[verticeCount - 1].Position = new Vector3(pathPoints[0].X, pathPoints[0].Y, zCoord); }
private void CreateOpenRectGeometry() { float centerX = X; float centerY = Y; float radius = Width / 2; float length = (float)Width; int segments = (int)(length / 12f) + 1; int segmentsHigh = (int)(Height / 12f) + 1; int totalPoints = (((segments+1) * 2 )+((segmentsHigh+1)*2 ))*2; if (points == null) { points = new PositionColoredTextured[totalPoints]; } for (int j = 0; j <= segments; j++) { int i = j * 2; points[i].Position = MakePosition(centerX, centerY, (float)((double)j / (double)segments) * (Width) - (Width / 2), (float)((Height / 2)), RotationAngle).Vector4; points[i].Tu = ((j) % 2); points[i].Tv = 0; points[i].Color = Color; points[i + 1].Position = MakePosition(centerX, centerY, (float)((double)j / (double)segments) * (Width) - (Width / 2), (float)((Height / 2) - 12f), RotationAngle).Vector4; points[i + 1].Tu = (j % 2); points[i + 1].Tv = 1; points[i + 1].Color = Color; int k = (((segments+1) * 4)+((segmentsHigh+1)*2)-2)-i; points[k].Position = MakePosition(centerX, centerY, (float)((double)j / (double)segments) * (Width) - (Width / 2), (float)(-(Height / 2)) + 12f, RotationAngle).Vector4; points[k].Tu = ((j) % 2); points[k].Tv = 0; points[k].Color = Color; points[k+1].Position = MakePosition(centerX, centerY, (float)((double)j / (double)segments) * (Width) - (Width / 2), (float)(-(Height / 2)), RotationAngle).Vector4; points[k + 1].Tu = (j % 2); points[k + 1].Tv = 1; points[k + 1].Color = Color; } int offset = ((segments+1) * 2); for (int j = 0; j <= segmentsHigh; j++) { int top = ((segmentsHigh+1) * 2)+offset-2; int i = j * 2 ; points[top - i].Position = MakePosition(centerX, centerY, (float)(Width / 2), (float)(((double)j / (double)segmentsHigh) * (Height) - (Height / 2)), RotationAngle).Vector4; points[top-i].Tu = ((j) % 2); points[top-i].Tv = 0; points[top-i].Color = Color; points[top - i + 1].Position = MakePosition(centerX, centerY, (float)((Width / 2) - 12f), (float)(((double)j / (double)segmentsHigh) * Height - ((Height / 2))), RotationAngle).Vector4; points[top-i + 1].Tu = (j % 2); points[top-i + 1].Tv = 1; points[top-i + 1].Color = Color; int k = i + ((segments + 1) * 4) + ((segmentsHigh + 1) * 2); points[k].Position = MakePosition(centerX, centerY, (float)(-(Width / 2) + 12), (float)(((double)j / (double)segmentsHigh) * (Height) - (Height / 2)), RotationAngle).Vector4; points[k].Tu = ((j) % 2); points[k].Tv = 0; points[k].Color = Color; points[k + 1].Position = MakePosition(centerX, centerY, (float)(- (Width / 2)), (float)(((double)j / (double)segmentsHigh) * Height - ((Height / 2))), RotationAngle).Vector4; points[k + 1].Tu = (j % 2); points[k + 1].Tv = 1; points[k + 1].Color = Color; } }
/// <summary> /// Converts the graphics path to an array of vertices using TriangleList. /// </summary> /// <param name="points">The points of the line.</param> /// <param name="thickness">The thickness of the line.</param> /// <param name="close">True if we should connect the first and last point.</param> /// <param name="zCoord">Z coordinate of the returned vertices.</param> /// <param name="lineJoin">The PenLineJoin to use.</param> /// <param name="verts">The generated verts.</param> public static void TriangulateStroke_TriangleList(PointF[] points, float thickness, bool close, float zCoord, PenLineJoin lineJoin, out PositionColoredTextured[] verts) { verts = null; PointF[] pathPoints = AdjustPoints(points); if (pathPoints.Length <= 0) return; int pointCount; if (close) pointCount = pathPoints.Length; else pointCount = pathPoints.Length - 1; int pointsLength = pathPoints.Length; List<PositionColoredTextured> vertList = new List<PositionColoredTextured>(); PointF[] lastLine = new PointF[] { PointF.Empty, PointF.Empty }; if (close) GetLastLine(pathPoints, out lastLine); for (int i = 0; i < pointCount; i++) { PointF currentPoint = pathPoints[i]; PointF nextPoint = GetNextPoint(pathPoints, i, pointsLength); PointF movedCurrent = PointF.Empty; PointF movedNext = PointF.Empty; MoveVector(currentPoint, nextPoint, thickness, ref movedCurrent, ref movedNext); if (lastLine[0] != PointF.Empty && lastLine[1] != PointF.Empty) { // We move the original line by the needed thickness. PointF movedLast0 = PointF.Empty; PointF movedLast1 = PointF.Empty; MoveVector(lastLine[0], lastLine[1], thickness, ref movedLast0, ref movedLast1); // StrokeLineJoin implementation switch (lineJoin) { case PenLineJoin.Round: // We fallback to the Miter because we don't support the Round line join yet. case PenLineJoin.Miter: // We need to calculate the intersection of the 2 moved lines (Line A: movedCurrent/movedNext and Line B: movedLast0/movedLast1) PointF intersection; if (LineIntersect(movedCurrent, movedNext, movedLast0, movedLast1, out intersection)) { vertList.Add(new PositionColoredTextured { Position = new Vector3(currentPoint.X, currentPoint.Y, zCoord) }); vertList.Add(new PositionColoredTextured { Position = new Vector3(movedCurrent.X, movedCurrent.Y, zCoord) }); vertList.Add(new PositionColoredTextured { Position = new Vector3(intersection.X, intersection.Y, zCoord) }); vertList.Add(new PositionColoredTextured { Position = new Vector3(currentPoint.X, currentPoint.Y, zCoord) }); vertList.Add(new PositionColoredTextured { Position = new Vector3(movedLast1.X, movedLast1.Y, zCoord) }); vertList.Add(new PositionColoredTextured { Position = new Vector3(intersection.X, intersection.Y, zCoord) }); } break; case PenLineJoin.Bevel: // This is currently not the exact WPF "Bevel" implementation, we only insert a simple triangle between the line ends. vertList.Add(new PositionColoredTextured { Position = new Vector3(currentPoint.X, currentPoint.Y, zCoord) }); vertList.Add(new PositionColoredTextured { Position = new Vector3(movedCurrent.X, movedCurrent.Y, zCoord) }); vertList.Add(new PositionColoredTextured { Position = new Vector3(movedLast1.X, movedLast1.Y, zCoord) }); break; } } vertList.Add(new PositionColoredTextured { Position = new Vector3(currentPoint.X, currentPoint.Y, zCoord) }); vertList.Add(new PositionColoredTextured { Position = new Vector3(nextPoint.X, nextPoint.Y, zCoord) }); vertList.Add(new PositionColoredTextured { Position = new Vector3(movedCurrent.X, movedCurrent.Y, zCoord) }); vertList.Add(new PositionColoredTextured { Position = new Vector3(nextPoint.X, nextPoint.Y, zCoord) }); vertList.Add(new PositionColoredTextured { Position = new Vector3(movedNext.X, movedNext.Y, zCoord) }); vertList.Add(new PositionColoredTextured { Position = new Vector3(movedCurrent.X, movedCurrent.Y, zCoord) }); lastLine = new PointF[] { currentPoint, nextPoint }; } verts = vertList.ToArray(); }
public override void InitiaizeGeometry() { currentRotation = 0; if (points == null) { points = new PositionColoredTextured[4]; } points[0].Position = MakePosition(X, Y, -Width / 2, -Height / 2, RotationAngle).Vector4; points[0].Tu = 0; points[0].Tv = 0; points[0].Color = Color.White; points[1].Position = MakePosition(X, Y, Width / 2, -Height / 2, RotationAngle).Vector4; points[1].Tu = 1; points[1].Tv = 0; points[1].Color = Color.White; points[2].Position = MakePosition(X, Y, -Width / 2, Height / 2, RotationAngle).Vector4; points[2].Tu = 0; points[2].Tv = 1; points[2].Color = Color.White; points[3].Position = MakePosition(X, Y, Width / 2, Height / 2, RotationAngle).Vector4; points[3].Tu = 1; points[3].Tv = 1; points[3].Color = Color.White; }
/// <summary> /// Creates a <see cref="PrimitiveType.TriangleList"/> of vertices which cover the interior of the /// specified <paramref name="points"/>. The path must be closed and describe a simple polygon. /// </summary> /// <param name="points">Points describing the border of a simple polygon.</param> /// <param name="zCoord">Z coordinate of the created vertices.</param> /// <param name="verts">Returns a <see cref="PrimitiveType.TriangleList"/> of vertices.</param> public static void Triangulate(PointF[] points, float zCoord, out PositionColoredTextured[] verts) { PointF[] pathPoints = AdjustPoints(points); if (pathPoints.Length < 3) { verts = null; return; } if (pathPoints.Length == 3) { verts = new PositionColoredTextured[3]; verts[0].Position = new Vector3(pathPoints[0].X, pathPoints[0].Y, zCoord); verts[1].Position = new Vector3(pathPoints[1].X, pathPoints[1].Y, zCoord); verts[2].Position = new Vector3(pathPoints[2].X, pathPoints[2].Y, zCoord); return; } IList<DelaunayTriangle> polygons; try { // Triangulation can fail (i.e. polygon is self-intersecting) var poly = new Poly2Tri.Polygon(pathPoints.Select(p => new PolygonPoint(p.X, p.Y))); P2T.Triangulate(poly); polygons = poly.Triangles; } catch (Exception) { verts = null; return; } verts = new PositionColoredTextured[polygons.Count * 3]; int offset = 0; foreach (DelaunayTriangle triangle in polygons) { verts[offset++].Position = new Vector3((float)triangle.Points[0].X, (float)triangle.Points[0].Y, zCoord); verts[offset++].Position = new Vector3((float)triangle.Points[1].X, (float)triangle.Points[1].Y, zCoord); verts[offset++].Position = new Vector3((float)triangle.Points[2].X, (float)triangle.Points[2].Y, zCoord); } }
public static MeshGroup FromFbx(string filePath) { const float Scale = 1.0f; var assimp = new Assimp.AssimpContext(); var scene = assimp.ImportFile(filePath, Assimp.PostProcessSteps.PreTransformVertices); var BoneScene = assimp.ImportFile(filePath); var baseFilePath = Path.GetDirectoryName(filePath); TexList = new List <string>(); TextureData = new List <Tm2>(); BoneData = new List <Assimp.Bone>(); NodeData = new List <Assimp.Node>(); foreach (Assimp.Material mat in scene.Materials) { Stream str = null; var name = Path.GetFileName(mat.TextureDiffuse.FilePath); if (name != "" || name != null) { str = File.OpenRead(name); } if (str != null) { TexList.Add(Path.GetFileName(mat.TextureDiffuse.FilePath)); PngImage png = new PngImage(str); Tm2 tmImage = Tm2.Create(png); TextureData.Add(tmImage); } } Assimp.Bone rBone = new Assimp.Bone(); foreach (var m in BoneScene.Meshes) { foreach (var bn in m.Bones) { if (!BoneData.Contains(bn)) { BoneData.Add(bn); } } } NodeData.AddRange(BoneScene.RootNode.Children.ToList()); return(new MeshGroup() { MeshDescriptors = scene.Meshes .Select(x => { var vertices = new PositionColoredTextured[x.Vertices.Count]; for (var i = 0; i < vertices.Length; i++) { vertices[i].X = x.Vertices[i].X * Scale; vertices[i].Y = x.Vertices[i].Y * Scale; vertices[i].Z = x.Vertices[i].Z * Scale; vertices[i].Tu = x.TextureCoordinateChannels[0][i].X; vertices[i].Tv = 1.0f - x.TextureCoordinateChannels[0][i].Y; vertices[i].R = x.VertexColorChannels[0][i].R; vertices[i].G = x.VertexColorChannels[0][i].G; vertices[i].B = x.VertexColorChannels[0][i].B; vertices[i].A = x.VertexColorChannels[0][i].A; } return new MeshDescriptor { Vertices = vertices, Indices = x.GetIndices(), IsOpaque = true, TextureIndex = x.MaterialIndex }; }).ToList() }); }
/// <summary> /// Generates the vertices of a thickened line strip. /// </summary> /// <param name="points">Points of the line strip</param> /// <param name="thickness">Thickness of the line</param> /// <param name="close">Whether to connect the last point back to the first</param> /// <param name="widthMode">How to place the weight of the line relative to it</param> /// <param name="zCoord">Z coordinate of the returned vertices.</param> /// <param name="verts">Generated vertices.</param> public static void CalculateLinePoints(PointF[] points, float thickness, bool close, WidthMode widthMode, float zCoord, out PositionColoredTextured[] verts) { PointF[] pathPoints = AdjustPoints(points); verts = null; if (pathPoints.Length < 3) { if (close) { return; } if (pathPoints.Length < 2) { return; } } int count = pathPoints.Length; if (pathPoints[count - 2] == pathPoints[count - 1]) { count--; } Vector2[] vPoints = new Vector2[count]; for (int i = 0; i < count; ++i) { vPoints[i] = new Vector2(pathPoints[i].X, pathPoints[i].Y); } Vector2 innerDistance = new Vector2(0, 0); switch (widthMode) { case WidthMode.Centered: //innerDistance =thickness / 2; innerDistance = new Vector2(thickness / 2, thickness / 2); break; case WidthMode.LeftHanded: //innerDistance = -thickness; innerDistance = new Vector2(-thickness, -thickness); break; case WidthMode.RightHanded: //innerDistance = thickness; innerDistance = new Vector2(thickness, thickness); break; } Vector2[] outPoints = new Vector2[(vPoints.Length + (close ? 1 : 0)) * 2]; float slope, intercept; //Get the endpoints if (close) { //Get the overlap points int lastIndex = outPoints.Length - 4; outPoints[lastIndex] = InnerPoint(innerDistance, vPoints[vPoints.Length - 2], vPoints[vPoints.Length - 1], vPoints[0], out slope, out intercept); outPoints[0] = InnerPoint(innerDistance, ref slope, ref intercept, outPoints[lastIndex], vPoints[0], vPoints[1]); } else { //Take endpoints based on the end segments' normals alone outPoints[0] = Vector2.Multiply(innerDistance, GetNormal(vPoints[1] - vPoints[0])); outPoints[0] = vPoints[0] + outPoints[0]; //outPoints[0] = points[0] + innerDistance * normal(points[1] - points[0]); Vector2 norm = Vector2.Multiply(innerDistance, GetNormal(vPoints[vPoints.Length - 1] - vPoints[vPoints.Length - 2])); //DEBUG outPoints[outPoints.Length - 2] = vPoints[vPoints.Length - 1] + norm; //Get the slope and intercept of the first segment to feed into the middle loop slope = VectorSlope(vPoints[1] - vPoints[0]); intercept = LineIntercept(outPoints[0], slope); } //Get the middle points for (int i = 1; i < vPoints.Length - 1; i++) { outPoints[2 * i] = InnerPoint(innerDistance, ref slope, ref intercept, outPoints[2 * (i - 1)], vPoints[i], vPoints[i + 1]); } //Derive the outer points from the inner points if (widthMode == WidthMode.Centered) { for (int i = 0; i < vPoints.Length; i++) { outPoints[2 * i + 1] = 2 * vPoints[i] - outPoints[2 * i]; } } else { for (int i = 0; i < vPoints.Length; i++) { outPoints[2 * i + 1] = vPoints[i]; } } //Closed strips must repeat the first two points if (close) { outPoints[outPoints.Length - 2] = outPoints[0]; outPoints[outPoints.Length - 1] = outPoints[1]; } int verticeCount = outPoints.Length; verts = new PositionColoredTextured[verticeCount]; for (int i = 0; i < verticeCount; ++i) { verts[i].Position = new Vector3(outPoints[i].X, outPoints[i].Y, zCoord); } }