public bool needSupportAt(IntPoint pointToCheckIfNeedsSupport, int z) { if (pointToCheckIfNeedsSupport.X < 1 || pointToCheckIfNeedsSupport.Y < 1 || pointToCheckIfNeedsSupport.X >= supportStorage.gridWidth - 1 || pointToCheckIfNeedsSupport.Y >= supportStorage.gridHeight - 1 || done[pointToCheckIfNeedsSupport.X + pointToCheckIfNeedsSupport.Y * supportStorage.gridWidth]) { return(false); } int gridIndex = (int)(pointToCheckIfNeedsSupport.X + pointToCheckIfNeedsSupport.Y * supportStorage.gridWidth); if (generateInternalSupport) { // We add 2 each time as we are wanting to look at the bottom face (even faces), and the intersections are bottom - top - bottom - top - etc. for (int zIndex = 0; zIndex < supportStorage.xYGridOfSupportPoints[gridIndex].Count; zIndex += 2) { SupportPoint currentBottomSupportPoint = supportStorage.xYGridOfSupportPoints[gridIndex][zIndex]; bool angleNeedsSupport = currentBottomSupportPoint.cosAngle >= cosAngle; if (angleNeedsSupport) { bool zIsBelowBottomSupportPoint = z <= currentBottomSupportPoint.z - interfaceZDistance_um - supportZDistance_um - extraErrorGap; if (zIndex == 0) { if (zIsBelowBottomSupportPoint) { return(true); } } else { SupportPoint previousTopSupportPoint = supportStorage.xYGridOfSupportPoints[gridIndex][zIndex - 1]; bool zIsAbovePrevSupportPoint = z > previousTopSupportPoint.z + supportZDistance_um; if (zIsBelowBottomSupportPoint && zIsAbovePrevSupportPoint) { return(true); } } } } return(false); } else // we only ever look up to the first point needing support (the 0th index) { if (supportStorage.xYGridOfSupportPoints[gridIndex].Count == 0) { // there are no points needing support here return(false); } if (supportStorage.xYGridOfSupportPoints[gridIndex][0].cosAngle < cosAngle) { // The angle does not need support return(false); } if (z >= supportStorage.xYGridOfSupportPoints[gridIndex][0].z - interfaceZDistance_um - supportZDistance_um - extraErrorGap) { // the spot is above the place we need to support return(false); } } return(true); }
public void GenerateSupportGrid(OptimizedModel model, ConfigSettings config) { this.generated = false; if (config.supportEndAngle < 0) { return; } this.generated = true; this.gridOffset.X = model.minXYZ_um.x; this.gridOffset.Y = model.minXYZ_um.y; this.gridScale = 200; this.gridWidth = (model.size_um.x / this.gridScale) + 1; this.gridHeight = (model.size_um.y / this.gridScale) + 1; int gridSize = this.gridWidth * this.gridHeight; this.xYGridOfSupportPoints = new List <List <SupportPoint> >(gridSize); for (int i = 0; i < gridSize; i++) { this.xYGridOfSupportPoints.Add(new List <SupportPoint>()); } this.endAngleDegrees = config.supportEndAngle; this.generateInternalSupport = config.generateInternalSupport; this.supportXYDistance_um = config.supportXYDistance_um; this.supportLayerHeight_um = config.layerThickness_um; this.supportZGapLayers = config.supportNumberOfLayersToSkipInZ; this.supportInterfaceLayers = config.supportInterfaceLayers; // This should really be a ray intersection as later code is going to count on it being an even odd list of bottoms and tops. // As it is we are finding the hit on the plane but not checking for good intersection with the triangle. for (int volumeIndex = 0; volumeIndex < model.volumes.Count; volumeIndex++) { OptimizedVolume vol = model.volumes[volumeIndex]; for (int faceIndex = 0; faceIndex < vol.facesTriangle.Count; faceIndex++) { OptimizedFace faceTriangle = vol.facesTriangle[faceIndex]; Point3 v0 = vol.vertices[faceTriangle.vertexIndex[0]].position; Point3 v1 = vol.vertices[faceTriangle.vertexIndex[1]].position; Point3 v2 = vol.vertices[faceTriangle.vertexIndex[2]].position; // get the angle of this polygon double angleFromHorizon; { FPoint3 v0f = new FPoint3(v0); FPoint3 v1f = new FPoint3(v1); FPoint3 v2f = new FPoint3(v2); FPoint3 normal = (v1f - v0f).Cross(v2f - v0f); normal.z = Math.Abs(normal.z); angleFromHorizon = (Math.PI / 2) - FPoint3.CalculateAngle(normal, FPoint3.Up); } v0.x = (int)((v0.x - this.gridOffset.X) / (double)this.gridScale + .5); v0.y = (int)((v0.y - this.gridOffset.Y) / (double)this.gridScale + .5); v1.x = (int)((v1.x - this.gridOffset.X) / (double)this.gridScale + .5); v1.y = (int)((v1.y - this.gridOffset.Y) / (double)this.gridScale + .5); v2.x = (int)((v2.x - this.gridOffset.X) / (double)this.gridScale + .5); v2.y = (int)((v2.y - this.gridOffset.Y) / (double)this.gridScale + .5); if (v0.x > v1.x) { swap(ref v0, ref v1); } if (v1.x > v2.x) { swap(ref v1, ref v2); } if (v0.x > v1.x) { swap(ref v0, ref v1); } for (long x = v0.x; x < v1.x; x++) { long y0 = (long)(v0.y + (v1.y - v0.y) * (x - v0.x) / (double)(v1.x - v0.x) + .5); long y1 = (long)(v0.y + (v2.y - v0.y) * (x - v0.x) / (double)(v2.x - v0.x) + .5); long z0 = (long)(v0.z + (v1.z - v0.z) * (x - v0.x) / (double)(v1.x - v0.x) + .5); long z1 = (long)(v0.z + (v2.z - v0.z) * (x - v0.x) / (double)(v2.x - v0.x) + .5); if (y0 > y1) { swap(ref y0, ref y1); swap(ref z0, ref z1); } for (long y = y0; y < y1; y++) { SupportPoint newSupportPoint = new SupportPoint((int)(z0 + (z1 - z0) * (y - y0) / (double)(y1 - y0) + .5), angleFromHorizon); this.xYGridOfSupportPoints[(int)(x + y * this.gridWidth)].Add(newSupportPoint); } } for (int x = v1.x; x < v2.x; x++) { long y0 = (long)(v1.y + (v2.y - v1.y) * (x - v1.x) / (double)(v2.x - v1.x) + .5); long y1 = (long)(v0.y + (v2.y - v0.y) * (x - v0.x) / (double)(v2.x - v0.x) + .5); long z0 = (long)(v1.z + (v2.z - v1.z) * (x - v1.x) / (double)(v2.x - v1.x) + .5); long z1 = (long)(v0.z + (v2.z - v0.z) * (x - v0.x) / (double)(v2.x - v0.x) + .5); if (y0 > y1) { swap(ref y0, ref y1); swap(ref z0, ref z1); } for (int y = (int)y0; y < y1; y++) { this.xYGridOfSupportPoints[x + y * this.gridWidth].Add(new SupportPoint((int)(z0 + (z1 - z0) * (double)(y - y0) / (double)(y1 - y0) + .5), angleFromHorizon)); } } } } for (int x = 0; x < this.gridWidth; x++) { for (int y = 0; y < this.gridHeight; y++) { int gridIndex = x + y * this.gridWidth; List <SupportPoint> currentList = this.xYGridOfSupportPoints[gridIndex]; currentList.Sort(SortSupportsOnZ); if (currentList.Count > 1) { // now remove duplicates (try to make it a better bottom and top list) for (int i = currentList.Count - 1; i >= 1; i--) { if (currentList[i].z == currentList[i - 1].z) { currentList.RemoveAt(i); } } } } } this.gridOffset.X += this.gridScale / 2; this.gridOffset.Y += this.gridScale / 2; }
private static int SortSupportsOnZ(SupportPoint one, SupportPoint two) { return one.z.CompareTo(two.z); }
private static int SortSupportsOnZ(SupportPoint one, SupportPoint two) { return(one.z.CompareTo(two.z)); }
public void GenerateSupportGrid(OptimizedModel model, ConfigSettings config) { this.generated = false; if (config.supportEndAngle < 0) { return; } this.generated = true; this.gridOffset.X = model.minXYZ_um.x; this.gridOffset.Y = model.minXYZ_um.y; this.gridScale = 200; this.gridWidth = (model.size_um.x / this.gridScale) + 1; this.gridHeight = (model.size_um.y / this.gridScale) + 1; int gridSize = this.gridWidth * this.gridHeight; this.xYGridOfSupportPoints = new List<List<SupportPoint>>(gridSize); for (int i = 0; i < gridSize; i++) { this.xYGridOfSupportPoints.Add(new List<SupportPoint>()); } this.endAngleDegrees = config.supportEndAngle; this.generateInternalSupport = config.generateInternalSupport; this.supportXYDistance_um = config.supportXYDistance_um; this.supportLayerHeight_um = config.layerThickness_um; this.supportZGapLayers = config.supportNumberOfLayersToSkipInZ; this.supportInterfaceLayers = config.supportInterfaceLayers; // This should really be a ray intersection as later code is going to count on it being an even odd list of bottoms and tops. // As it is we are finding the hit on the plane but not checking for good intersection with the triangle. for (int volumeIndex = 0; volumeIndex < model.volumes.Count; volumeIndex++) { OptimizedVolume vol = model.volumes[volumeIndex]; for (int faceIndex = 0; faceIndex < vol.facesTriangle.Count; faceIndex++) { OptimizedFace faceTriangle = vol.facesTriangle[faceIndex]; Point3 v0 = vol.vertices[faceTriangle.vertexIndex[0]].position; Point3 v1 = vol.vertices[faceTriangle.vertexIndex[1]].position; Point3 v2 = vol.vertices[faceTriangle.vertexIndex[2]].position; // get the angle of this polygon double angleFromHorizon; { FPoint3 v0f = new FPoint3(v0); FPoint3 v1f = new FPoint3(v1); FPoint3 v2f = new FPoint3(v2); FPoint3 normal = (v1f - v0f).Cross(v2f - v0f); normal.z = Math.Abs(normal.z); angleFromHorizon = (Math.PI / 2) - FPoint3.CalculateAngle(normal, FPoint3.Up); } v0.x = (int)((v0.x - this.gridOffset.X) / (double)this.gridScale + .5); v0.y = (int)((v0.y - this.gridOffset.Y) / (double)this.gridScale + .5); v1.x = (int)((v1.x - this.gridOffset.X) / (double)this.gridScale + .5); v1.y = (int)((v1.y - this.gridOffset.Y) / (double)this.gridScale + .5); v2.x = (int)((v2.x - this.gridOffset.X) / (double)this.gridScale + .5); v2.y = (int)((v2.y - this.gridOffset.Y) / (double)this.gridScale + .5); if (v0.x > v1.x) swap(ref v0, ref v1); if (v1.x > v2.x) swap(ref v1, ref v2); if (v0.x > v1.x) swap(ref v0, ref v1); for (long x = v0.x; x < v1.x; x++) { long y0 = (long)(v0.y + (v1.y - v0.y) * (x - v0.x) / (double)(v1.x - v0.x) + .5); long y1 = (long)(v0.y + (v2.y - v0.y) * (x - v0.x) / (double)(v2.x - v0.x) + .5); long z0 = (long)(v0.z + (v1.z - v0.z) * (x - v0.x) / (double)(v1.x - v0.x) + .5); long z1 = (long)(v0.z + (v2.z - v0.z) * (x - v0.x) / (double)(v2.x - v0.x) + .5); if (y0 > y1) { swap(ref y0, ref y1); swap(ref z0, ref z1); } for (long y = y0; y < y1; y++) { SupportPoint newSupportPoint = new SupportPoint((int)(z0 + (z1 - z0) * (y - y0) / (double)(y1 - y0) + .5), angleFromHorizon); this.xYGridOfSupportPoints[(int)(x + y * this.gridWidth)].Add(newSupportPoint); } } for (int x = v1.x; x < v2.x; x++) { long y0 = (long)(v1.y + (v2.y - v1.y) * (x - v1.x) / (double)(v2.x - v1.x) + .5); long y1 = (long)(v0.y + (v2.y - v0.y) * (x - v0.x) / (double)(v2.x - v0.x) + .5); long z0 = (long)(v1.z + (v2.z - v1.z) * (x - v1.x) / (double)(v2.x - v1.x) + .5); long z1 = (long)(v0.z + (v2.z - v0.z) * (x - v0.x) / (double)(v2.x - v0.x) + .5); if (y0 > y1) { swap(ref y0, ref y1); swap(ref z0, ref z1); } for (int y = (int)y0; y < y1; y++) { this.xYGridOfSupportPoints[x + y * this.gridWidth].Add(new SupportPoint((int)(z0 + (z1 - z0) * (double)(y - y0) / (double)(y1 - y0) + .5), angleFromHorizon)); } } } } for (int x = 0; x < this.gridWidth; x++) { for (int y = 0; y < this.gridHeight; y++) { int gridIndex = x + y * this.gridWidth; List<SupportPoint> currentList = this.xYGridOfSupportPoints[gridIndex]; currentList.Sort(SortSupportsOnZ); if (currentList.Count > 1) { // now remove duplicates (try to make it a better bottom and top list) for (int i = currentList.Count - 1; i >= 1; i--) { if (currentList[i].z == currentList[i - 1].z) { currentList.RemoveAt(i); } } } } } this.gridOffset.X += this.gridScale / 2; this.gridOffset.Y += this.gridScale / 2; }