2017-06-29 17:11:17 -07:00
|
|
|
|
/*
|
2019-01-15 12:23:40 -08:00
|
|
|
|
Copyright (c) 2019, Lars Brubaker, John Lewin
|
2014-02-15 18:06:03 -08:00
|
|
|
|
All rights reserved.
|
|
|
|
|
|
|
|
|
|
|
|
Redistribution and use in source and binary forms, with or without
|
2015-04-08 15:20:10 -07:00
|
|
|
|
modification, are permitted provided that the following conditions are met:
|
2014-02-15 18:06:03 -08:00
|
|
|
|
|
|
|
|
|
|
1. Redistributions of source code must retain the above copyright notice, this
|
2015-04-08 15:20:10 -07:00
|
|
|
|
list of conditions and the following disclaimer.
|
2014-02-15 18:06:03 -08:00
|
|
|
|
2. Redistributions in binary form must reproduce the above copyright notice,
|
|
|
|
|
|
this list of conditions and the following disclaimer in the documentation
|
2015-04-08 15:20:10 -07:00
|
|
|
|
and/or other materials provided with the distribution.
|
2014-02-15 18:06:03 -08:00
|
|
|
|
|
|
|
|
|
|
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
|
|
|
|
|
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
|
|
|
|
|
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
|
|
|
|
|
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR
|
|
|
|
|
|
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
|
|
|
|
|
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
|
|
|
|
|
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
|
|
|
|
|
|
ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
|
|
|
|
|
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
|
|
|
|
|
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
|
|
|
|
|
|
|
|
|
|
The views and conclusions contained in the software and documentation are those
|
2015-04-08 15:20:10 -07:00
|
|
|
|
of the authors and should not be interpreted as representing official policies,
|
2014-02-15 18:06:03 -08:00
|
|
|
|
either expressed or implied, of the FreeBSD Project.
|
|
|
|
|
|
*/
|
2015-04-08 15:20:10 -07:00
|
|
|
|
|
2014-02-15 18:06:03 -08:00
|
|
|
|
using System;
|
2014-01-29 19:09:30 -08:00
|
|
|
|
using System.Collections.Generic;
|
|
|
|
|
|
using System.Diagnostics;
|
2014-06-11 14:52:58 -07:00
|
|
|
|
using System.IO;
|
2018-02-05 17:37:42 -08:00
|
|
|
|
using System.Linq;
|
2018-07-08 16:07:22 -07:00
|
|
|
|
using System.Text;
|
2014-06-11 14:52:58 -07:00
|
|
|
|
using System.Threading;
|
2017-06-29 19:42:20 -07:00
|
|
|
|
using System.Threading.Tasks;
|
2017-06-29 17:11:17 -07:00
|
|
|
|
using MatterHackers.Agg;
|
2017-08-20 02:34:39 -07:00
|
|
|
|
using MatterHackers.Agg.Platform;
|
2017-06-29 17:11:17 -07:00
|
|
|
|
using MatterHackers.DataConverters3D;
|
|
|
|
|
|
using MatterHackers.MatterControl.DataStorage;
|
2018-08-17 17:49:41 -07:00
|
|
|
|
using MatterHackers.MatterControl.PartPreviewWindow;
|
2017-06-29 17:11:17 -07:00
|
|
|
|
using MatterHackers.MatterControl.SettingsManagement;
|
|
|
|
|
|
using MatterHackers.PolygonMesh;
|
2018-07-31 12:50:48 -07:00
|
|
|
|
using MatterHackers.PolygonMesh.Processors;
|
2018-02-05 17:37:42 -08:00
|
|
|
|
using MatterHackers.VectorMath;
|
2014-01-29 19:09:30 -08:00
|
|
|
|
|
2014-02-15 18:06:03 -08:00
|
|
|
|
namespace MatterHackers.MatterControl.SlicerConfiguration
|
2014-01-29 19:09:30 -08:00
|
|
|
|
{
|
2017-10-17 12:42:52 -07:00
|
|
|
|
public static class Slicer
|
2015-04-08 15:20:10 -07:00
|
|
|
|
{
|
2017-10-17 12:42:52 -07:00
|
|
|
|
private static Dictionary<Mesh, MeshPrintOutputSettings> meshPrintOutputSettings = new Dictionary<Mesh, MeshPrintOutputSettings>();
|
2014-01-29 19:09:30 -08:00
|
|
|
|
|
2015-04-08 15:20:10 -07:00
|
|
|
|
public static List<bool> extrudersUsed = new List<bool>();
|
2018-09-23 19:22:44 -07:00
|
|
|
|
public static bool RunInProcess { get; set; } = false;
|
2017-10-16 17:09:00 -07:00
|
|
|
|
|
2018-08-23 12:40:34 -07:00
|
|
|
|
public static List<(Matrix4X4 matrix, string fileName)> GetStlFileLocations(IObject3D object3D, ref string mergeRules, PrinterConfig printer, IProgress<ProgressStatus> progressReporter, CancellationToken cancellationToken)
|
2015-04-08 15:20:10 -07:00
|
|
|
|
{
|
2017-12-11 14:15:50 -08:00
|
|
|
|
var progressStatus = new ProgressStatus();
|
|
|
|
|
|
|
2015-04-08 15:20:10 -07:00
|
|
|
|
extrudersUsed.Clear();
|
|
|
|
|
|
|
2017-11-16 22:01:24 -08:00
|
|
|
|
int extruderCount = printer.Settings.GetValue<int>(SettingsKey.extruder_count);
|
2015-04-08 15:20:10 -07:00
|
|
|
|
for (int extruderIndex = 0; extruderIndex < extruderCount; extruderIndex++)
|
|
|
|
|
|
{
|
|
|
|
|
|
extrudersUsed.Add(false);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
2016-01-04 21:18:57 -08:00
|
|
|
|
// If we have support enabled and are using an extruder other than 0 for it
|
2019-01-03 16:05:02 -08:00
|
|
|
|
if (object3D.VisibleMeshes().Any(i => i.WorldOutputType() == PrintOutputTypes.Support))
|
2015-04-08 15:20:10 -07:00
|
|
|
|
{
|
2019-01-11 14:39:40 -08:00
|
|
|
|
if (printer.Settings.GetValue<int>(SettingsKey.support_material_extruder) != 0)
|
2015-04-08 15:20:10 -07:00
|
|
|
|
{
|
2019-01-11 14:39:40 -08:00
|
|
|
|
int supportExtruder = Math.Max(0, Math.Min(printer.Settings.GetValue<int>(SettingsKey.extruder_count) - 1, printer.Settings.GetValue<int>(SettingsKey.support_material_extruder) - 1));
|
2015-04-08 15:20:10 -07:00
|
|
|
|
extrudersUsed[supportExtruder] = true;
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// If we have raft enabled and are using an extruder other than 0 for it
|
2019-01-06 11:33:06 -08:00
|
|
|
|
if (printer.Settings.GetValue<bool>(SettingsKey.create_raft))
|
2015-04-08 15:20:10 -07:00
|
|
|
|
{
|
2019-01-11 14:39:40 -08:00
|
|
|
|
if (printer.Settings.GetValue<int>(SettingsKey.raft_extruder) != 0)
|
2015-04-08 15:20:10 -07:00
|
|
|
|
{
|
2019-01-11 14:39:40 -08:00
|
|
|
|
int raftExtruder = Math.Max(0, Math.Min(printer.Settings.GetValue<int>(SettingsKey.extruder_count) - 1, printer.Settings.GetValue<int>(SettingsKey.raft_extruder) - 1));
|
2015-04-08 15:20:10 -07:00
|
|
|
|
extrudersUsed[raftExtruder] = true;
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
{
|
2018-07-08 16:07:22 -07:00
|
|
|
|
// TODO: Once graph parsing is added to MatterSlice we can remove and avoid this flattening
|
|
|
|
|
|
meshPrintOutputSettings.Clear();
|
2017-11-16 22:13:35 -08:00
|
|
|
|
|
2018-07-08 16:07:22 -07:00
|
|
|
|
// Flatten the scene, filtering out items outside of the build volume
|
2018-08-23 13:24:48 -07:00
|
|
|
|
var meshItemsOnBuildPlate = printer.PrintableItems(object3D);
|
2018-07-08 16:07:22 -07:00
|
|
|
|
if (meshItemsOnBuildPlate.Any())
|
|
|
|
|
|
{
|
|
|
|
|
|
int maxExtruderIndex = 0;
|
2018-02-05 17:37:42 -08:00
|
|
|
|
|
2018-07-08 16:07:22 -07:00
|
|
|
|
var itemsByExtruder = new List<IEnumerable<IObject3D>>();
|
|
|
|
|
|
for (int extruderIndexIn = 0; extruderIndexIn < extruderCount; extruderIndexIn++)
|
|
|
|
|
|
{
|
|
|
|
|
|
var extruderIndex = extruderIndexIn;
|
|
|
|
|
|
var itemsThisExtruder = meshItemsOnBuildPlate.Where((item) =>
|
2018-08-13 18:59:15 -07:00
|
|
|
|
(File.Exists(item.MeshPath) // Drop missing files
|
|
|
|
|
|
|| File.Exists(Path.Combine(Object3D.AssetsPath, item.MeshPath)))
|
2018-08-13 17:57:06 -07:00
|
|
|
|
&& (item.WorldMaterialIndex() == extruderIndex
|
2018-07-08 16:07:22 -07:00
|
|
|
|
|| (extruderIndex == 0
|
|
|
|
|
|
&& (item.WorldMaterialIndex() >= extruderCount || item.WorldMaterialIndex() == -1)))
|
|
|
|
|
|
&& (item.WorldOutputType() == PrintOutputTypes.Solid || item.WorldOutputType() == PrintOutputTypes.Default));
|
|
|
|
|
|
|
2018-08-13 17:51:19 -07:00
|
|
|
|
itemsByExtruder.Add(itemsThisExtruder);
|
2018-07-08 16:07:22 -07:00
|
|
|
|
extrudersUsed[extruderIndex] |= itemsThisExtruder.Any();
|
|
|
|
|
|
if (extrudersUsed[extruderIndex])
|
2015-05-26 17:07:55 -07:00
|
|
|
|
{
|
2018-07-08 16:07:22 -07:00
|
|
|
|
maxExtruderIndex = extruderIndex;
|
2015-04-08 15:20:10 -07:00
|
|
|
|
}
|
2018-07-08 16:07:22 -07:00
|
|
|
|
}
|
2015-04-08 15:20:10 -07:00
|
|
|
|
|
2018-07-08 16:07:22 -07:00
|
|
|
|
var outputOptions = new List<(Matrix4X4 matrix, string fileName)>();
|
2018-02-05 17:37:42 -08:00
|
|
|
|
|
2018-07-08 16:07:22 -07:00
|
|
|
|
int savedStlCount = 0;
|
|
|
|
|
|
bool first = true;
|
|
|
|
|
|
for (int extruderIndex = 0; extruderIndex < itemsByExtruder.Count; extruderIndex++)
|
|
|
|
|
|
{
|
|
|
|
|
|
if (!first)
|
2015-04-08 15:20:10 -07:00
|
|
|
|
{
|
2018-07-08 16:07:22 -07:00
|
|
|
|
mergeRules += ",";
|
2018-08-13 17:57:57 -07:00
|
|
|
|
first = false;
|
2018-02-05 17:37:42 -08:00
|
|
|
|
}
|
2015-04-08 15:20:10 -07:00
|
|
|
|
|
2018-08-13 17:57:57 -07:00
|
|
|
|
mergeRules += AddObjectsForExtruder(itemsByExtruder[extruderIndex], outputOptions, ref savedStlCount);
|
|
|
|
|
|
}
|
2017-06-15 16:54:36 -07:00
|
|
|
|
|
2018-08-13 17:57:57 -07:00
|
|
|
|
var supportObjects = meshItemsOnBuildPlate.Where((item) => item.WorldOutputType() == PrintOutputTypes.Support);
|
2017-05-19 14:39:57 -07:00
|
|
|
|
|
2018-07-31 12:21:44 -07:00
|
|
|
|
// if we added user generated support
|
2018-07-08 16:07:22 -07:00
|
|
|
|
if (supportObjects.Any())
|
|
|
|
|
|
{
|
|
|
|
|
|
// add a flag to the merge rules to let us know there was support
|
2019-01-30 16:04:12 -08:00
|
|
|
|
mergeRules += ",S" + AddObjectsForExtruder(supportObjects, outputOptions, ref savedStlCount);
|
2018-07-08 16:07:22 -07:00
|
|
|
|
}
|
2017-07-21 11:17:02 -07:00
|
|
|
|
|
2018-07-08 16:07:22 -07:00
|
|
|
|
mergeRules += " ";
|
2018-02-05 18:11:28 -08:00
|
|
|
|
|
2018-07-08 16:07:22 -07:00
|
|
|
|
return outputOptions;
|
|
|
|
|
|
}
|
2018-02-05 17:37:42 -08:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
return new List<(Matrix4X4 matrix, string fileName)>();
|
|
|
|
|
|
}
|
|
|
|
|
|
|
2018-02-05 18:11:28 -08:00
|
|
|
|
private static string AddObjectsForExtruder(IEnumerable<IObject3D> items,
|
2018-02-05 17:37:42 -08:00
|
|
|
|
List<(Matrix4X4 matrix, string fileName)> outputItems,
|
|
|
|
|
|
ref int savedStlCount)
|
|
|
|
|
|
{
|
|
|
|
|
|
string mergeString = "";
|
2018-02-05 18:11:28 -08:00
|
|
|
|
if (items.Any())
|
2018-02-05 17:37:42 -08:00
|
|
|
|
{
|
2018-02-05 18:11:28 -08:00
|
|
|
|
bool first = true;
|
|
|
|
|
|
foreach (var item in items)
|
2018-02-05 17:37:42 -08:00
|
|
|
|
{
|
2018-02-05 18:11:28 -08:00
|
|
|
|
if (!first)
|
|
|
|
|
|
{
|
|
|
|
|
|
mergeString += ",";
|
|
|
|
|
|
}
|
2018-07-31 12:50:48 -07:00
|
|
|
|
|
|
|
|
|
|
// TODO: Use existing AssetsPath property
|
2018-02-05 18:11:28 -08:00
|
|
|
|
string assetsDirectory = Path.Combine(ApplicationDataStorage.Instance.ApplicationLibraryDataPath, "Assets");
|
|
|
|
|
|
outputItems.Add((item.WorldMatrix(), Path.Combine(assetsDirectory, item.MeshPath)));
|
|
|
|
|
|
mergeString += $"({savedStlCount++}";
|
|
|
|
|
|
first = false;
|
2018-02-05 17:37:42 -08:00
|
|
|
|
}
|
|
|
|
|
|
|
2018-02-05 18:11:28 -08:00
|
|
|
|
mergeString += new String(')', items.Count());
|
|
|
|
|
|
}
|
|
|
|
|
|
else
|
|
|
|
|
|
{
|
2018-07-31 12:50:48 -07:00
|
|
|
|
// TODO: consider dropping the custom path and using the AssetPath as above
|
|
|
|
|
|
string folderToSaveStlsTo = Path.Combine(ApplicationDataStorage.Instance.ApplicationTempDataPath, "amf_to_stl");
|
2018-02-05 17:37:42 -08:00
|
|
|
|
|
2018-07-31 12:50:48 -07:00
|
|
|
|
// Create directory if needed
|
|
|
|
|
|
Directory.CreateDirectory(folderToSaveStlsTo);
|
2015-04-08 15:20:10 -07:00
|
|
|
|
|
2018-07-31 12:50:48 -07:00
|
|
|
|
Mesh tinyMesh = PlatonicSolids.CreateCube(.001, .001, .001);
|
2017-06-29 17:11:17 -07:00
|
|
|
|
|
2018-10-25 14:23:56 -07:00
|
|
|
|
string tinyObjectFileName = Path.Combine(folderToSaveStlsTo, Path.ChangeExtension("non_printing_extruder_change_mesh", ".stl"));
|
2017-06-29 17:11:17 -07:00
|
|
|
|
|
2018-07-31 12:50:48 -07:00
|
|
|
|
StlProcessing.Save(tinyMesh, tinyObjectFileName, CancellationToken.None);
|
2017-06-29 17:11:17 -07:00
|
|
|
|
|
2018-07-31 12:50:48 -07:00
|
|
|
|
outputItems.Add((Matrix4X4.Identity, tinyObjectFileName));
|
|
|
|
|
|
mergeString += $"({savedStlCount++})";
|
|
|
|
|
|
}
|
2017-06-29 17:11:17 -07:00
|
|
|
|
|
2018-07-31 12:50:48 -07:00
|
|
|
|
return mergeString;
|
2015-12-14 08:29:24 -08:00
|
|
|
|
}
|
|
|
|
|
|
|
2018-02-09 18:11:55 -08:00
|
|
|
|
public static Task<bool> SliceItem(IObject3D object3D, string gcodeFilePath, PrinterConfig printer, IProgress<ProgressStatus> progressReporter, CancellationToken cancellationToken)
|
2017-06-29 19:42:20 -07:00
|
|
|
|
{
|
|
|
|
|
|
string mergeRules = "";
|
|
|
|
|
|
|
2018-02-09 18:11:55 -08:00
|
|
|
|
var stlFileLocations = GetStlFileLocations(object3D, ref mergeRules, printer, progressReporter, cancellationToken);
|
2017-12-11 14:15:50 -08:00
|
|
|
|
|
2018-12-05 11:27:59 -08:00
|
|
|
|
if (stlFileLocations.Count > 0)
|
|
|
|
|
|
{
|
|
|
|
|
|
return SliceItem(stlFileLocations, mergeRules, gcodeFilePath, printer, progressReporter, cancellationToken);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
return Task.FromResult(false);
|
2018-02-12 14:52:47 -08:00
|
|
|
|
}
|
|
|
|
|
|
|
2018-08-17 17:49:41 -07:00
|
|
|
|
public static Task<bool> SliceItem(List<(Matrix4X4 matrix, string fileName)> stlFileLocations, string mergeRules, string gcodeFilePath, PrinterConfig printer, IProgress<ProgressStatus> reporter, CancellationToken cancellationToken)
|
2018-02-12 14:52:47 -08:00
|
|
|
|
{
|
2018-08-17 17:49:41 -07:00
|
|
|
|
// Wrap the reporter with a specialized MatterSlice string parser for percent from string results
|
|
|
|
|
|
var sliceProgressReporter = new SliceProgressReporter(reporter, printer);
|
|
|
|
|
|
|
2018-02-12 14:52:47 -08:00
|
|
|
|
bool slicingSucceeded = true;
|
|
|
|
|
|
|
2018-02-05 17:37:42 -08:00
|
|
|
|
if(stlFileLocations.Count > 0)
|
2017-06-29 19:42:20 -07:00
|
|
|
|
{
|
2017-12-11 14:15:50 -08:00
|
|
|
|
var progressStatus = new ProgressStatus()
|
|
|
|
|
|
{
|
|
|
|
|
|
Status = "Generating Config"
|
|
|
|
|
|
};
|
2018-08-17 17:49:41 -07:00
|
|
|
|
sliceProgressReporter.Report(progressStatus);
|
2017-12-11 14:15:50 -08:00
|
|
|
|
|
2017-06-29 19:42:20 -07:00
|
|
|
|
string configFilePath = Path.Combine(
|
|
|
|
|
|
ApplicationDataStorage.Instance.GCodeOutputPath,
|
2017-11-16 22:01:24 -08:00
|
|
|
|
string.Format("config_{0}.ini", printer.Settings.GetLongHashCode().ToString()));
|
2017-06-29 19:42:20 -07:00
|
|
|
|
|
2017-12-11 14:15:50 -08:00
|
|
|
|
progressStatus.Status = "Starting slicer";
|
2018-08-17 17:49:41 -07:00
|
|
|
|
sliceProgressReporter.Report(progressStatus);
|
2017-12-11 14:15:50 -08:00
|
|
|
|
|
2018-01-31 09:50:23 -08:00
|
|
|
|
if (!File.Exists(gcodeFilePath)
|
|
|
|
|
|
|| !HasCompletedSuccessfully(gcodeFilePath))
|
2017-06-29 19:42:20 -07:00
|
|
|
|
{
|
|
|
|
|
|
string commandArgs;
|
|
|
|
|
|
|
2018-08-03 13:00:15 -07:00
|
|
|
|
var matrixAndMeshArgs = new StringBuilder();
|
2018-02-05 17:37:42 -08:00
|
|
|
|
foreach (var matrixAndFile in stlFileLocations)
|
2017-06-29 19:42:20 -07:00
|
|
|
|
{
|
2018-02-10 21:08:24 -08:00
|
|
|
|
var matrixString = "";
|
2018-02-05 17:37:42 -08:00
|
|
|
|
bool first = true;
|
|
|
|
|
|
for (int i = 0; i < 4; i++)
|
|
|
|
|
|
{
|
|
|
|
|
|
for (int j = 0; j < 4; j++)
|
|
|
|
|
|
{
|
2018-07-08 16:07:22 -07:00
|
|
|
|
if (!first)
|
2018-02-05 17:37:42 -08:00
|
|
|
|
{
|
2018-02-10 21:08:24 -08:00
|
|
|
|
matrixString += ",";
|
2018-02-05 17:37:42 -08:00
|
|
|
|
}
|
2018-02-10 21:08:24 -08:00
|
|
|
|
matrixString += matrixAndFile.matrix[i, j].ToString("0.######");
|
2018-02-05 17:37:42 -08:00
|
|
|
|
first = false;
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
2018-07-08 16:07:22 -07:00
|
|
|
|
matrixAndMeshArgs.Append($" -m \"{matrixString}\"");
|
|
|
|
|
|
matrixAndMeshArgs.Append($" \"{matrixAndFile.fileName}\" ");
|
2017-06-29 19:42:20 -07:00
|
|
|
|
}
|
|
|
|
|
|
|
2018-11-13 18:43:27 -08:00
|
|
|
|
printer.EngineMappingsMatterSlice.WriteSliceSettingsFile(configFilePath, rawLines: new[]
|
2018-08-29 17:15:47 -07:00
|
|
|
|
{
|
|
|
|
|
|
$"booleanOperations = {mergeRules}",
|
|
|
|
|
|
$"additionalArgsToProcess ={matrixAndMeshArgs}"
|
|
|
|
|
|
});
|
2018-07-08 16:07:22 -07:00
|
|
|
|
|
|
|
|
|
|
commandArgs = $"-v -o \"{gcodeFilePath}\" -c \"{configFilePath}\"";
|
|
|
|
|
|
|
2018-11-08 05:38:46 -08:00
|
|
|
|
bool forcedExit = false;
|
|
|
|
|
|
|
2017-08-20 02:34:39 -07:00
|
|
|
|
if (AggContext.OperatingSystem == OSType.Android
|
|
|
|
|
|
|| AggContext.OperatingSystem == OSType.Mac
|
2018-09-02 13:50:43 -07:00
|
|
|
|
|| RunInProcess)
|
2017-06-29 19:42:20 -07:00
|
|
|
|
{
|
2017-12-11 14:15:50 -08:00
|
|
|
|
EventHandler WriteOutput = (s, e) =>
|
2017-09-25 11:11:54 -07:00
|
|
|
|
{
|
2018-11-08 05:38:46 -08:00
|
|
|
|
if (cancellationToken.IsCancellationRequested)
|
2018-01-31 08:14:00 -08:00
|
|
|
|
{
|
2018-09-05 16:56:00 -07:00
|
|
|
|
MatterHackers.MatterSlice.MatterSlice.Stop();
|
2018-11-08 05:38:46 -08:00
|
|
|
|
forcedExit = true;
|
2018-01-31 08:14:00 -08:00
|
|
|
|
}
|
2018-11-08 05:38:46 -08:00
|
|
|
|
|
2017-12-11 14:15:50 -08:00
|
|
|
|
if (s is string stringValue)
|
2017-09-25 11:11:54 -07:00
|
|
|
|
{
|
2018-08-17 17:49:41 -07:00
|
|
|
|
sliceProgressReporter?.Report(new ProgressStatus()
|
2017-12-11 14:15:50 -08:00
|
|
|
|
{
|
|
|
|
|
|
Status = stringValue
|
|
|
|
|
|
});
|
2017-09-25 11:11:54 -07:00
|
|
|
|
}
|
|
|
|
|
|
};
|
|
|
|
|
|
|
2017-12-11 14:15:50 -08:00
|
|
|
|
MatterSlice.LogOutput.GetLogWrites += WriteOutput;
|
2017-09-25 11:11:54 -07:00
|
|
|
|
|
2017-06-29 19:42:20 -07:00
|
|
|
|
MatterSlice.MatterSlice.ProcessArgs(commandArgs);
|
2017-09-25 11:11:54 -07:00
|
|
|
|
|
2017-12-11 14:15:50 -08:00
|
|
|
|
MatterSlice.LogOutput.GetLogWrites -= WriteOutput;
|
2018-11-08 05:38:46 -08:00
|
|
|
|
|
|
|
|
|
|
slicingSucceeded = !forcedExit;
|
2017-06-29 19:42:20 -07:00
|
|
|
|
}
|
|
|
|
|
|
else
|
|
|
|
|
|
{
|
2018-02-01 21:25:02 -08:00
|
|
|
|
var slicerProcess = new Process()
|
2017-06-29 19:42:20 -07:00
|
|
|
|
{
|
|
|
|
|
|
StartInfo = new ProcessStartInfo()
|
2015-04-08 15:20:10 -07:00
|
|
|
|
{
|
2017-06-29 19:42:20 -07:00
|
|
|
|
Arguments = commandArgs,
|
|
|
|
|
|
CreateNoWindow = true,
|
|
|
|
|
|
WindowStyle = ProcessWindowStyle.Hidden,
|
|
|
|
|
|
RedirectStandardError = true,
|
|
|
|
|
|
RedirectStandardOutput = true,
|
|
|
|
|
|
FileName = MatterSliceInfo.GetEnginePath(),
|
|
|
|
|
|
UseShellExecute = false
|
2015-04-08 15:20:10 -07:00
|
|
|
|
}
|
2017-06-29 19:42:20 -07:00
|
|
|
|
};
|
|
|
|
|
|
|
2017-12-11 14:15:50 -08:00
|
|
|
|
slicerProcess.OutputDataReceived += (s, e) =>
|
2017-06-29 19:42:20 -07:00
|
|
|
|
{
|
2017-12-11 14:15:50 -08:00
|
|
|
|
if (e.Data is string stringValue)
|
2015-04-08 15:20:10 -07:00
|
|
|
|
{
|
2018-02-01 21:25:02 -08:00
|
|
|
|
if (cancellationToken.IsCancellationRequested)
|
|
|
|
|
|
{
|
|
|
|
|
|
slicerProcess?.Kill();
|
|
|
|
|
|
slicerProcess?.Dispose();
|
|
|
|
|
|
forcedExit = true;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
2017-12-11 14:15:50 -08:00
|
|
|
|
string message = stringValue.Replace("=>", "").Trim();
|
2017-06-29 19:42:20 -07:00
|
|
|
|
if (message.Contains(".gcode"))
|
Move to new library model and view
- Add new listview control for library content
- Migrate library providers to containers
- Cloud, Sqlite, Directories, Queue, History
- Migrate SideBar components to containers
- Primatives, Text, Braille, ImageConverter
- Create new library container types
- Zip files, Calibration parts, Printer SDCards
- Reduce leftnav to Library, Settings, Controls, Options
- Add DragDrop support for image content
2017-05-19 22:33:55 -07:00
|
|
|
|
{
|
2017-06-29 19:42:20 -07:00
|
|
|
|
message = "Saving intermediate file";
|
|
|
|
|
|
}
|
|
|
|
|
|
message += "...";
|
2015-04-08 15:20:10 -07:00
|
|
|
|
|
2018-08-17 17:49:41 -07:00
|
|
|
|
sliceProgressReporter?.Report(new ProgressStatus()
|
2017-12-11 14:15:50 -08:00
|
|
|
|
{
|
|
|
|
|
|
Status = message
|
|
|
|
|
|
});
|
2017-06-29 19:42:20 -07:00
|
|
|
|
}
|
|
|
|
|
|
};
|
Move to new library model and view
- Add new listview control for library content
- Migrate library providers to containers
- Cloud, Sqlite, Directories, Queue, History
- Migrate SideBar components to containers
- Primatives, Text, Braille, ImageConverter
- Create new library container types
- Zip files, Calibration parts, Printer SDCards
- Reduce leftnav to Library, Settings, Controls, Options
- Add DragDrop support for image content
2017-05-19 22:33:55 -07:00
|
|
|
|
|
2017-06-29 19:42:20 -07:00
|
|
|
|
slicerProcess.Start();
|
|
|
|
|
|
slicerProcess.BeginOutputReadLine();
|
2015-04-08 15:20:10 -07:00
|
|
|
|
|
2017-06-29 19:42:20 -07:00
|
|
|
|
string stdError = slicerProcess.StandardError.ReadToEnd();
|
2015-04-08 15:20:10 -07:00
|
|
|
|
|
2018-02-01 21:25:02 -08:00
|
|
|
|
if (!forcedExit)
|
2017-06-29 19:42:20 -07:00
|
|
|
|
{
|
2018-02-01 21:25:02 -08:00
|
|
|
|
slicerProcess.WaitForExit();
|
2017-06-29 19:42:20 -07:00
|
|
|
|
}
|
2018-02-01 21:42:09 -08:00
|
|
|
|
|
|
|
|
|
|
slicingSucceeded = !forcedExit;
|
2017-06-29 19:42:20 -07:00
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
try
|
|
|
|
|
|
{
|
2018-11-08 05:38:46 -08:00
|
|
|
|
if (slicingSucceeded
|
|
|
|
|
|
&& File.Exists(gcodeFilePath)
|
2017-06-29 19:42:20 -07:00
|
|
|
|
&& File.Exists(configFilePath))
|
|
|
|
|
|
{
|
|
|
|
|
|
// make sure we have not already written the settings onto this file
|
|
|
|
|
|
bool fileHasSettings = false;
|
|
|
|
|
|
int bufferSize = 32000;
|
|
|
|
|
|
using (Stream fileStream = File.OpenRead(gcodeFilePath))
|
|
|
|
|
|
{
|
|
|
|
|
|
// Read the tail of the file to determine if the given token exists
|
|
|
|
|
|
byte[] buffer = new byte[bufferSize];
|
|
|
|
|
|
fileStream.Seek(Math.Max(0, fileStream.Length - bufferSize), SeekOrigin.Begin);
|
|
|
|
|
|
int numBytesRead = fileStream.Read(buffer, 0, bufferSize);
|
|
|
|
|
|
string fileEnd = System.Text.Encoding.UTF8.GetString(buffer);
|
|
|
|
|
|
if (fileEnd.Contains("GCode settings used"))
|
|
|
|
|
|
{
|
|
|
|
|
|
fileHasSettings = true;
|
2015-04-08 15:20:10 -07:00
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
2017-06-29 19:42:20 -07:00
|
|
|
|
if (!fileHasSettings)
|
2015-04-08 15:20:10 -07:00
|
|
|
|
{
|
2017-06-29 19:42:20 -07:00
|
|
|
|
using (StreamWriter gcodeWriter = File.AppendText(gcodeFilePath))
|
2015-04-08 15:20:10 -07:00
|
|
|
|
{
|
2017-06-29 19:42:20 -07:00
|
|
|
|
string oemName = "MatterControl";
|
|
|
|
|
|
if (OemSettings.Instance.WindowTitleExtra != null && OemSettings.Instance.WindowTitleExtra.Trim().Length > 0)
|
2015-01-20 10:45:34 -08:00
|
|
|
|
{
|
2017-06-29 19:42:20 -07:00
|
|
|
|
oemName += $" - {OemSettings.Instance.WindowTitleExtra}";
|
2015-01-20 10:45:34 -08:00
|
|
|
|
}
|
|
|
|
|
|
|
2017-06-29 19:42:20 -07:00
|
|
|
|
gcodeWriter.WriteLine("; {0} Version {1} Build {2} : GCode settings used", oemName, VersionInfo.Instance.ReleaseVersion, VersionInfo.Instance.BuildVersion);
|
|
|
|
|
|
gcodeWriter.WriteLine("; Date {0} Time {1}:{2:00}", DateTime.Now.Date, DateTime.Now.Hour, DateTime.Now.Minute);
|
2015-01-20 10:45:34 -08:00
|
|
|
|
|
2017-06-29 19:42:20 -07:00
|
|
|
|
foreach (string line in File.ReadLines(configFilePath))
|
|
|
|
|
|
{
|
|
|
|
|
|
gcodeWriter.WriteLine("; {0}", line);
|
2015-01-20 10:45:34 -08:00
|
|
|
|
}
|
2015-04-08 15:20:10 -07:00
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
2017-06-29 19:42:20 -07:00
|
|
|
|
catch (Exception)
|
|
|
|
|
|
{
|
|
|
|
|
|
}
|
2015-04-08 15:20:10 -07:00
|
|
|
|
}
|
2017-12-11 14:15:50 -08:00
|
|
|
|
|
2018-02-01 21:42:09 -08:00
|
|
|
|
return Task.FromResult(slicingSucceeded);
|
2015-04-08 15:20:10 -07:00
|
|
|
|
}
|
|
|
|
|
|
|
2018-01-31 09:50:23 -08:00
|
|
|
|
private static bool HasCompletedSuccessfully(string gcodeFilePath)
|
2015-04-08 15:20:10 -07:00
|
|
|
|
{
|
2018-01-31 09:50:23 -08:00
|
|
|
|
using (var reader = new StreamReader(gcodeFilePath))
|
2015-01-13 10:34:27 -08:00
|
|
|
|
{
|
2018-02-01 17:25:42 -08:00
|
|
|
|
if (reader.BaseStream.Length > 10000)
|
2015-01-13 10:34:27 -08:00
|
|
|
|
{
|
2018-02-01 17:25:42 -08:00
|
|
|
|
reader.BaseStream.Seek(-10000, SeekOrigin.End);
|
2015-01-13 10:34:27 -08:00
|
|
|
|
}
|
2018-02-01 17:25:42 -08:00
|
|
|
|
|
2018-01-31 09:50:23 -08:00
|
|
|
|
string endText = reader.ReadToEnd();
|
|
|
|
|
|
|
2018-02-01 17:25:42 -08:00
|
|
|
|
return endText.Contains("; MatterSlice Completed Successfully");
|
2015-01-13 10:34:27 -08:00
|
|
|
|
}
|
2015-04-08 15:20:10 -07:00
|
|
|
|
}
|
|
|
|
|
|
}
|
2017-08-20 02:34:39 -07:00
|
|
|
|
}
|