2014-01-29 19:09:30 -08:00
/ *
2014-02-15 18:06:03 -08:00
Copyright ( c ) 2014 , Lars Brubaker
2014-01-29 19:09:30 -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-01-29 19:09:30 -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-01-29 19:09:30 -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-01-29 19:09:30 -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-01-29 19:09:30 -08:00
either expressed or implied , of the FreeBSD Project .
* /
2015-12-22 15:26:51 -08:00
//#define DoBooleanTest
2014-01-29 19:09:30 -08:00
using MatterHackers.Agg ;
2015-04-08 15:20:10 -07:00
using MatterHackers.Agg.Transform ;
2014-01-29 19:09:30 -08:00
using MatterHackers.Agg.UI ;
2014-11-22 20:35:40 -08:00
using MatterHackers.Agg.VertexSource ;
2014-10-15 14:11:14 -07:00
using MatterHackers.Localizations ;
2014-10-23 14:40:12 -07:00
using MatterHackers.MatterControl.CustomWidgets ;
using MatterHackers.MatterControl.DataStorage ;
2014-06-11 14:52:58 -07:00
using MatterHackers.MatterControl.PrinterCommunication ;
2015-06-17 15:43:37 -07:00
using MatterHackers.MatterControl.PrintLibrary.Provider ;
2014-04-15 18:13:27 -07:00
using MatterHackers.MatterControl.PrintQueue ;
2014-10-13 18:20:01 -07:00
using MatterHackers.MatterControl.SlicerConfiguration ;
2014-01-29 19:09:30 -08:00
using MatterHackers.MeshVisualizer ;
2014-04-15 18:13:27 -07:00
using MatterHackers.PolygonMesh ;
2014-01-29 19:09:30 -08:00
using MatterHackers.PolygonMesh.Processors ;
using MatterHackers.RayTracer ;
using MatterHackers.RayTracer.Traceable ;
2014-04-15 18:13:27 -07:00
using MatterHackers.RenderOpenGl ;
using MatterHackers.VectorMath ;
2015-04-08 15:20:10 -07:00
using System ;
using System.Collections.Generic ;
using System.Collections.ObjectModel ;
using System.Diagnostics ;
using System.Globalization ;
using System.IO ;
using System.Threading ;
2015-07-02 11:23:44 -07:00
using System.Threading.Tasks ;
2014-01-29 19:09:30 -08:00
namespace MatterHackers.MatterControl.PartPreviewWindow
{
2015-04-08 15:20:10 -07:00
public partial class View3DWidget : PartPreview3DWidget
{
2015-05-30 12:48:16 -07:00
internal HeightValueDisplay heightDisplay ;
2015-04-08 15:20:10 -07:00
private readonly int EditButtonHeight = 44 ;
2015-06-24 16:59:10 -07:00
private Action afterSaveCallback = null ;
2015-05-30 12:48:16 -07:00
private Button applyScaleButton ;
private List < MeshGroup > asynchMeshGroups = new List < MeshGroup > ( ) ;
private List < ScaleRotateTranslate > asynchMeshGroupTransforms = new List < ScaleRotateTranslate > ( ) ;
private List < PlatingMeshGroupData > asynchPlatingDatas = new List < PlatingMeshGroupData > ( ) ;
private FlowLayoutWidget doEdittingButtonsContainer ;
private bool editorThatRequestedSave = false ;
private FlowLayoutWidget enterEditButtonsContainer ;
private CheckBox expandMaterialOptions ;
private CheckBox expandMirrorOptions ;
private CheckBox expandRotateOptions ;
private CheckBox expandScaleOptions ;
private CheckBox expandViewOptions ;
private ExportPrintItemWindow exportingWindow = null ;
private ObservableCollection < GuiWidget > extruderButtons = new ObservableCollection < GuiWidget > ( ) ;
private bool firstDraw = true ;
private bool hasDrawn = false ;
private FlowLayoutWidget materialOptionContainer ;
private List < PlatingMeshGroupData > MeshGroupExtraData ;
2015-04-08 15:20:10 -07:00
private MeshSelectInfo meshSelectInfo ;
private FlowLayoutWidget mirrorOptionContainer ;
2015-05-30 12:48:16 -07:00
private OpenMode openMode ;
private bool partHasBeenEdited = false ;
2015-04-08 15:20:10 -07:00
private List < string > pendingPartsToLoad = new List < string > ( ) ;
2015-05-30 12:48:16 -07:00
private PrintItemWrapper printItemWrapper ;
2015-04-08 15:20:10 -07:00
private ProgressControl processingProgressControl ;
2015-05-30 12:48:16 -07:00
private FlowLayoutWidget rotateOptionContainer ;
private SaveAsWindow saveAsWindow = null ;
private SplitButton saveButtons ;
private bool saveSucceded = true ;
private FlowLayoutWidget scaleOptionContainer ;
2015-04-08 15:20:10 -07:00
private MHNumberEdit scaleRatioControl ;
2015-05-30 12:48:16 -07:00
private EventHandler SelectionChanged ;
private RGBA_Bytes [ ] SelectionColors = new RGBA_Bytes [ ] { new RGBA_Bytes ( 131 , 4 , 66 ) , new RGBA_Bytes ( 227 , 31 , 61 ) , new RGBA_Bytes ( 255 , 148 , 1 ) , new RGBA_Bytes ( 247 , 224 , 23 ) , new RGBA_Bytes ( 143 , 212 , 1 ) } ;
private EditableNumberDisplay [ ] sizeDisplay = new EditableNumberDisplay [ 3 ] ;
private Stopwatch timeSinceLastSpin = new Stopwatch ( ) ;
private Stopwatch timeSinceReported = new Stopwatch ( ) ;
private Dictionary < string , List < GuiWidget > > transformControls = new Dictionary < string , List < GuiWidget > > ( ) ;
private Matrix4X4 transformOnMouseDown = Matrix4X4 . Identity ;
private CheckBox uniformScale ;
private EventHandler unregisterEvents ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
private UpArrow3D upArrow ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
private bool viewIsInEditModePreLock = false ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
private FlowLayoutWidget viewOptionContainer ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
private bool wasInSelectMode = false ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
public View3DWidget ( PrintItemWrapper printItemWrapper , Vector3 viewerVolume , Vector2 bedCenter , MeshViewerWidget . BedShape bedShape , WindowMode windowType , AutoRotate autoRotate , OpenMode openMode = OpenMode . Viewing )
{
this . openMode = openMode ;
this . windowType = windowType ;
allowAutoRotate = ( autoRotate = = AutoRotate . Enabled ) ;
autoRotating = allowAutoRotate ;
MeshGroupExtraData = new List < PlatingMeshGroupData > ( ) ;
MeshGroupExtraData . Add ( new PlatingMeshGroupData ( ) ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
this . printItemWrapper = printItemWrapper ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
FlowLayoutWidget mainContainerTopToBottom = new FlowLayoutWidget ( FlowDirection . TopToBottom ) ;
mainContainerTopToBottom . HAnchor = Agg . UI . HAnchor . Max_FitToChildren_ParentWidth ;
mainContainerTopToBottom . VAnchor = Agg . UI . VAnchor . Max_FitToChildren_ParentHeight ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
FlowLayoutWidget centerPartPreviewAndControls = new FlowLayoutWidget ( FlowDirection . LeftToRight ) ;
centerPartPreviewAndControls . Name = "centerPartPreviewAndControls" ;
centerPartPreviewAndControls . AnchorAll ( ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
GuiWidget viewArea = new GuiWidget ( ) ;
viewArea . AnchorAll ( ) ;
{
meshViewerWidget = new MeshViewerWidget ( viewerVolume , bedCenter , bedShape , "Press 'Add' to select an item." . Localize ( ) ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
PutOemImageOnBed ( ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
meshViewerWidget . AnchorAll ( ) ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
viewArea . AddChild ( meshViewerWidget ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
centerPartPreviewAndControls . AddChild ( viewArea ) ;
mainContainerTopToBottom . AddChild ( centerPartPreviewAndControls ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
FlowLayoutWidget buttonBottomPanel = new FlowLayoutWidget ( FlowDirection . LeftToRight ) ;
buttonBottomPanel . HAnchor = HAnchor . ParentLeftRight ;
buttonBottomPanel . Padding = new BorderDouble ( 3 , 3 ) ;
buttonBottomPanel . BackgroundColor = ActiveTheme . Instance . PrimaryBackgroundColor ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
buttonRightPanel = CreateRightButtonPanel ( viewerVolume . y ) ;
buttonRightPanel . Name = "buttonRightPanel" ;
buttonRightPanel . Visible = false ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
CreateOptionsContent ( ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
// add in the plater tools
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
FlowLayoutWidget editToolBar = new FlowLayoutWidget ( ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
string progressFindPartsLabel = "Entering Editor" . Localize ( ) ;
string progressFindPartsLabelFull = "{0}:" . FormatWith ( progressFindPartsLabel ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
processingProgressControl = new ProgressControl ( progressFindPartsLabelFull , ActiveTheme . Instance . PrimaryTextColor , ActiveTheme . Instance . PrimaryAccentColor ) ;
processingProgressControl . VAnchor = Agg . UI . VAnchor . ParentCenter ;
editToolBar . AddChild ( processingProgressControl ) ;
editToolBar . VAnchor | = Agg . UI . VAnchor . ParentCenter ;
processingProgressControl . Visible = false ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
// If the window is embeded (in the center pannel) and there is no item loaded then don't show the add button
enterEditButtonsContainer = new FlowLayoutWidget ( ) ;
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
Button addButton = textImageButtonFactory . Generate ( "Insert" . Localize ( ) , "icon_insert_32x32.png" ) ;
2015-08-10 13:36:31 -07:00
addButton . ToolTipText = "Insert an .stl, .amf or .zip file" . Localize ( ) ;
2015-05-30 12:48:16 -07:00
addButton . Margin = new BorderDouble ( right : 0 ) ;
enterEditButtonsContainer . AddChild ( addButton ) ;
addButton . Click + = ( sender , e ) = >
2015-04-08 15:20:10 -07:00
{
2015-06-11 12:06:40 -07:00
UiThread . RunOnIdle ( ( ) = >
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
DoAddFileAfterCreatingEditData = true ;
EnterEditAndCreateSelectionData ( ) ;
} ) ;
} ;
2015-12-22 15:26:51 -08:00
if ( printItemWrapper ! = null
2015-07-14 16:44:05 -07:00
& & printItemWrapper . PrintItem . ReadOnly )
2015-07-13 10:08:08 -07:00
{
addButton . Enabled = false ;
}
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
Button enterEdittingButton = textImageButtonFactory . Generate ( "Edit" . Localize ( ) , "icon_edit_32x32.png" ) ;
2015-09-01 16:03:29 -07:00
enterEdittingButton . Name = "3D View Edit" ;
2015-05-30 12:48:16 -07:00
enterEdittingButton . Margin = new BorderDouble ( right : 4 ) ;
enterEdittingButton . Click + = ( sender , e ) = >
{
EnterEditAndCreateSelectionData ( ) ;
} ;
2015-12-22 15:26:51 -08:00
if ( printItemWrapper ! = null
2015-07-14 16:44:05 -07:00
& & printItemWrapper . PrintItem . ReadOnly )
2015-07-13 10:08:08 -07:00
{
enterEdittingButton . Enabled = false ;
}
2014-03-07 09:50:41 -08:00
2014-11-06 11:57:32 -08:00
Button exportButton = textImageButtonFactory . Generate ( "Export..." . Localize ( ) ) ;
2015-12-22 15:26:51 -08:00
if ( printItemWrapper ! = null & &
2015-07-14 16:44:05 -07:00
( printItemWrapper . PrintItem . Protected | | printItemWrapper . PrintItem . ReadOnly ) )
2015-07-13 10:08:08 -07:00
{
exportButton . Enabled = false ;
}
2014-10-10 14:52:50 -07:00
exportButton . Margin = new BorderDouble ( right : 10 ) ;
2015-04-08 15:20:10 -07:00
exportButton . Click + = ( sender , e ) = >
2014-10-10 14:52:50 -07:00
{
2015-06-11 12:06:40 -07:00
UiThread . RunOnIdle ( ( ) = >
2014-10-10 14:52:50 -07:00
{
OpenExportWindow ( ) ;
} ) ;
} ;
2015-04-08 15:20:10 -07:00
enterEditButtonsContainer . AddChild ( enterEdittingButton ) ;
2014-10-10 14:52:50 -07:00
enterEditButtonsContainer . AddChild ( exportButton ) ;
2015-04-08 15:20:10 -07:00
}
editToolBar . AddChild ( enterEditButtonsContainer ) ;
2014-01-29 19:09:30 -08:00
2015-04-08 15:20:10 -07:00
doEdittingButtonsContainer = new FlowLayoutWidget ( ) ;
doEdittingButtonsContainer . Visible = false ;
2014-01-29 19:09:30 -08:00
2015-04-08 15:20:10 -07:00
{
2014-12-20 09:07:13 -08:00
Button addButton = textImageButtonFactory . Generate ( "Insert" . Localize ( ) , "icon_insert_32x32.png" ) ;
2015-04-08 15:20:10 -07:00
addButton . Margin = new BorderDouble ( right : 10 ) ;
doEdittingButtonsContainer . AddChild ( addButton ) ;
addButton . Click + = ( sender , e ) = >
{
2015-06-11 12:06:40 -07:00
UiThread . RunOnIdle ( ( ) = >
2015-04-08 15:20:10 -07:00
{
FileDialog . OpenFileDialog (
new OpenFileDialogParams ( ApplicationSettings . OpenDesignFileParams , multiSelect : true ) ,
( openParams ) = >
{
LoadAndAddPartsToPlate ( openParams . FileNames ) ;
} ) ;
} ) ;
} ;
2014-01-29 19:09:30 -08:00
2014-12-20 09:07:13 -08:00
GuiWidget separator = new GuiWidget ( 1 , 2 ) ;
separator . BackgroundColor = ActiveTheme . Instance . PrimaryTextColor ;
separator . Margin = new BorderDouble ( 4 , 2 ) ;
separator . VAnchor = VAnchor . ParentBottomTop ;
doEdittingButtonsContainer . AddChild ( separator ) ;
2014-12-19 09:39:29 -08:00
2015-04-08 15:20:10 -07:00
Button ungroupButton = textImageButtonFactory . Generate ( "Ungroup" . Localize ( ) ) ;
doEdittingButtonsContainer . AddChild ( ungroupButton ) ;
ungroupButton . Click + = ( sender , e ) = >
{
UngroupSelectedMeshGroup ( ) ;
} ;
2014-10-13 18:20:01 -07:00
2015-04-08 15:20:10 -07:00
Button groupButton = textImageButtonFactory . Generate ( "Group" . Localize ( ) ) ;
doEdittingButtonsContainer . AddChild ( groupButton ) ;
groupButton . Click + = ( sender , e ) = >
{
GroupSelectedMeshs ( ) ;
} ;
2014-10-29 13:15:53 -07:00
2015-04-08 15:20:10 -07:00
Button alignButton = textImageButtonFactory . Generate ( "Align" . Localize ( ) ) ;
doEdittingButtonsContainer . AddChild ( alignButton ) ;
alignButton . Click + = ( sender , e ) = >
{
AlignToSelectedMeshGroup ( ) ;
} ;
2014-10-15 14:11:14 -07:00
2015-05-01 09:45:50 -07:00
Button arrangeButton = textImageButtonFactory . Generate ( "Arrange" . Localize ( ) ) ;
doEdittingButtonsContainer . AddChild ( arrangeButton ) ;
arrangeButton . Click + = ( sender , e ) = >
{
AutoArrangePartsInBackground ( ) ;
} ;
2014-12-20 09:07:13 -08:00
GuiWidget separatorTwo = new GuiWidget ( 1 , 2 ) ;
separatorTwo . BackgroundColor = ActiveTheme . Instance . PrimaryTextColor ;
separatorTwo . Margin = new BorderDouble ( 4 , 2 ) ;
separatorTwo . VAnchor = VAnchor . ParentBottomTop ;
doEdittingButtonsContainer . AddChild ( separatorTwo ) ;
2015-04-08 15:20:10 -07:00
Button copyButton = textImageButtonFactory . Generate ( "Copy" . Localize ( ) ) ;
2015-09-01 16:03:29 -07:00
copyButton . Name = "3D View Copy" ;
2015-04-08 15:20:10 -07:00
doEdittingButtonsContainer . AddChild ( copyButton ) ;
copyButton . Click + = ( sender , e ) = >
{
MakeCopyOfGroup ( ) ;
} ;
2014-01-29 19:09:30 -08:00
2015-04-08 15:20:10 -07:00
Button deleteButton = textImageButtonFactory . Generate ( "Remove" . Localize ( ) ) ;
2015-09-01 16:03:29 -07:00
deleteButton . Name = "3D View Delete" ;
2015-04-08 15:20:10 -07:00
doEdittingButtonsContainer . AddChild ( deleteButton ) ;
deleteButton . Click + = ( sender , e ) = >
{
DeleteSelectedMesh ( ) ;
} ;
2014-10-13 18:20:01 -07:00
2014-12-20 09:07:13 -08:00
GuiWidget separatorThree = new GuiWidget ( 1 , 2 ) ;
separatorThree . BackgroundColor = ActiveTheme . Instance . PrimaryTextColor ;
separatorThree . Margin = new BorderDouble ( 4 , 1 ) ;
separatorThree . VAnchor = VAnchor . ParentBottomTop ;
doEdittingButtonsContainer . AddChild ( separatorThree ) ;
Button leaveEditModeButton = textImageButtonFactory . Generate ( "Cancel" . Localize ( ) , centerText : true ) ;
leaveEditModeButton . Click + = ( sender , e ) = >
2015-04-15 16:39:37 -07:00
{
2015-06-11 12:06:40 -07:00
UiThread . RunOnIdle ( ( ) = >
2014-12-20 09:07:13 -08:00
{
2015-04-15 16:39:37 -07:00
if ( saveButtons . Visible )
{
StyledMessageBox . ShowMessageBox ( ExitEditingAndSaveIfRequired , "Would you like to save your changes before exiting the editor?" , "Save Changes" , StyledMessageBox . MessageType . YES_NO ) ;
}
else
{
if ( partHasBeenEdited )
2014-12-20 09:07:13 -08:00
{
2015-04-15 16:39:37 -07:00
ExitEditingAndSaveIfRequired ( false ) ;
}
else
{
SwitchStateToNotEditing ( ) ;
}
}
} ) ;
} ;
2014-12-20 09:07:13 -08:00
doEdittingButtonsContainer . AddChild ( leaveEditModeButton ) ;
// put in the save button
AddSaveAndSaveAs ( doEdittingButtonsContainer ) ;
2015-04-08 15:20:10 -07:00
}
2014-01-29 19:09:30 -08:00
2015-04-08 15:20:10 -07:00
KeyDown + = ( sender , e ) = >
{
KeyEventArgs keyEvent = e as KeyEventArgs ;
if ( keyEvent ! = null & & ! keyEvent . Handled )
{
if ( keyEvent . KeyCode = = Keys . Delete | | keyEvent . KeyCode = = Keys . Back )
{
DeleteSelectedMesh ( ) ;
}
if ( keyEvent . KeyCode = = Keys . Escape )
{
if ( meshSelectInfo . downOnPart )
{
meshSelectInfo . downOnPart = false ;
ScaleRotateTranslate translated = SelectedMeshGroupTransform ;
translated . translation = transformOnMouseDown ;
SelectedMeshGroupTransform = translated ;
2014-01-29 19:09:30 -08:00
2015-04-08 15:20:10 -07:00
Invalidate ( ) ;
}
}
}
} ;
2014-01-29 19:09:30 -08:00
2015-04-08 15:20:10 -07:00
editToolBar . AddChild ( doEdittingButtonsContainer ) ;
buttonBottomPanel . AddChild ( editToolBar ) ;
}
2014-01-29 19:09:30 -08:00
2015-04-08 15:20:10 -07:00
GuiWidget buttonRightPanelHolder = new GuiWidget ( HAnchor . FitToChildren , VAnchor . ParentBottomTop ) ;
2015-04-15 16:39:37 -07:00
buttonRightPanelHolder . Name = "buttonRightPanelHolder" ;
2015-04-08 15:20:10 -07:00
centerPartPreviewAndControls . AddChild ( buttonRightPanelHolder ) ;
buttonRightPanelHolder . AddChild ( buttonRightPanel ) ;
2015-09-04 09:55:40 -07:00
buttonRightPanel . VisibleChanged + = ( sender , e ) = >
{
buttonRightPanelHolder . Visible = buttonRightPanel . Visible ;
} ;
2014-05-25 11:11:11 -07:00
2015-04-08 15:20:10 -07:00
viewControls3D = new ViewControls3D ( meshViewerWidget ) ;
2014-10-24 13:53:00 -07:00
2015-11-09 12:36:47 -08:00
viewControls3D . ResetView + = ( sender , e ) = >
{
SetDefaultView ( ) ;
2015-12-22 15:26:51 -08:00
} ;
2015-11-09 12:36:47 -08:00
2015-04-08 15:20:10 -07:00
buttonRightPanelDisabledCover = new Cover ( HAnchor . ParentLeftRight , VAnchor . ParentBottomTop ) ;
buttonRightPanelDisabledCover . BackgroundColor = new RGBA_Bytes ( ActiveTheme . Instance . PrimaryBackgroundColor , 150 ) ;
buttonRightPanelHolder . AddChild ( buttonRightPanelDisabledCover ) ;
2014-01-29 19:09:30 -08:00
2015-04-08 15:20:10 -07:00
viewControls3D . PartSelectVisible = false ;
LockEditControls ( ) ;
2014-01-29 19:09:30 -08:00
2015-04-08 15:20:10 -07:00
GuiWidget leftRightSpacer = new GuiWidget ( ) ;
leftRightSpacer . HAnchor = HAnchor . ParentLeftRight ;
buttonBottomPanel . AddChild ( leftRightSpacer ) ;
2014-04-09 21:47:00 -07:00
2015-04-08 15:20:10 -07:00
if ( windowType = = WindowMode . StandAlone )
{
Button closeButton = textImageButtonFactory . Generate ( "Close" . Localize ( ) ) ;
buttonBottomPanel . AddChild ( closeButton ) ;
closeButton . Click + = ( sender , e ) = >
{
CloseOnIdle ( ) ;
} ;
}
2014-01-29 19:09:30 -08:00
2015-04-08 15:20:10 -07:00
mainContainerTopToBottom . AddChild ( buttonBottomPanel ) ;
2014-01-29 19:09:30 -08:00
2015-04-08 15:20:10 -07:00
this . AddChild ( mainContainerTopToBottom ) ;
this . AnchorAll ( ) ;
2014-01-29 19:09:30 -08:00
2015-04-08 15:20:10 -07:00
meshViewerWidget . TrackballTumbleWidget . TransformState = TrackBallController . MouseDownType . Rotation ;
AddChild ( viewControls3D ) ;
2014-03-01 23:27:34 -08:00
2015-04-08 15:20:10 -07:00
AddHandlers ( ) ;
2014-05-02 12:07:27 -07:00
2015-04-08 15:20:10 -07:00
UiThread . RunOnIdle ( AutoSpin ) ;
2014-05-27 09:16:35 -07:00
2015-04-08 15:20:10 -07:00
if ( printItemWrapper = = null & & windowType = = WindowMode . Embeded )
{
enterEditButtonsContainer . Visible = false ;
}
if ( windowType = = WindowMode . Embeded )
{
PrinterConnectionAndCommunication . Instance . CommunicationStateChanged . RegisterEvent ( SetEditControlsBasedOnPrinterState , ref unregisterEvents ) ;
if ( windowType = = WindowMode . Embeded )
{
// make sure we lock the controls if we are printing or paused
switch ( PrinterConnectionAndCommunication . Instance . CommunicationState )
{
case PrinterConnectionAndCommunication . CommunicationStates . Printing :
case PrinterConnectionAndCommunication . CommunicationStates . Paused :
LockEditControls ( ) ;
break ;
}
}
}
ActiveTheme . Instance . ThemeChanged . RegisterEvent ( ThemeChanged , ref unregisterEvents ) ;
upArrow = new UpArrow3D ( this ) ;
heightDisplay = new HeightValueDisplay ( this ) ;
heightDisplay . Visible = false ;
meshViewerWidget . interactionVolumes . Add ( upArrow ) ;
// make sure the colors are set correctl
ThemeChanged ( this , null ) ;
saveButtons . VisibleChanged + = ( sender , e ) = >
{
partHasBeenEdited = true ;
} ;
2015-11-09 12:36:47 -08:00
SetDefaultView ( ) ;
2015-12-22 15:26:51 -08:00
#if DoBooleanTest
DrawBefore + = CreateBooleanTestGeometry ;
DrawAfter + = RemoveBooleanTestGeometry ;
#endif
}
#if DoBooleanTest
MeshGroup booleanGroup ;
ScaleRotateTranslate groupTransform ;
Vector3 offset = new Vector3 ( ) ;
2015-12-22 17:56:49 -08:00
Vector3 direction = new Vector3 ( . 11 , . 12 , . 13 ) ;
2015-12-22 15:26:51 -08:00
Vector3 centering = new Vector3 ( 100 , 100 , 20 ) ;
private void CreateBooleanTestGeometry ( GuiWidget drawingWidget , DrawEventArgs e )
{
Mesh boxA = PlatonicSolids . CreateCube ( 40 , 40 , 40 ) ;
2015-12-22 17:56:49 -08:00
//boxA.Triangulate();
2015-12-22 15:26:51 -08:00
boxA . Translate ( centering ) ;
Mesh boxB = PlatonicSolids . CreateCube ( 40 , 40 , 40 ) ;
2015-12-22 17:56:49 -08:00
//boxB.Triangulate();
2015-12-22 15:26:51 -08:00
for ( int i = 0 ; i < 3 ; i + + )
{
if ( Math . Abs ( direction [ i ] + offset [ i ] ) > 10 )
{
direction [ i ] = - direction [ i ] ;
}
}
offset + = direction ;
boxB . Translate ( offset + centering ) ;
booleanGroup = new MeshGroup ( ) ;
booleanGroup . Meshes . Add ( PolygonMesh . Csg . CsgOperations . Union ( boxA , boxB ) ) ;
meshViewerWidget . MeshGroups . Add ( booleanGroup ) ;
groupTransform = ScaleRotateTranslate . Identity ( ) ;
meshViewerWidget . MeshGroupTransforms . Add ( groupTransform ) ;
}
private void RemoveBooleanTestGeometry ( GuiWidget drawingWidget , DrawEventArgs e )
{
meshViewerWidget . MeshGroups . Remove ( booleanGroup ) ;
meshViewerWidget . MeshGroupTransforms . Remove ( groupTransform ) ;
2015-12-22 17:56:49 -08:00
UiThread . RunOnIdle ( ( ) = > Invalidate ( ) , 1.0 / 30.0 ) ;
2015-12-22 15:26:51 -08:00
}
#endif
2015-04-08 15:20:10 -07:00
2015-11-09 12:36:47 -08:00
public override void SetDefaultView ( )
{
meshViewerWidget . TrackballTumbleWidget . ZeroVelocity ( ) ;
meshViewerWidget . TrackballTumbleWidget . TrackBallController . Reset ( ) ;
meshViewerWidget . TrackballTumbleWidget . TrackBallController . Scale = . 03 ;
meshViewerWidget . TrackballTumbleWidget . TrackBallController . Translate ( - new Vector3 ( ActiveSliceSettings . Instance . BedCenter ) ) ;
meshViewerWidget . TrackballTumbleWidget . TrackBallController . Rotate ( Quaternion . FromEulerAngles ( new Vector3 ( 0 , 0 , MathHelper . Tau / 16 ) ) ) ;
meshViewerWidget . TrackballTumbleWidget . TrackBallController . Rotate ( Quaternion . FromEulerAngles ( new Vector3 ( - MathHelper . Tau * . 19 , 0 , 0 ) ) ) ;
}
2015-12-22 15:26:51 -08:00
public enum AutoRotate { Enabled , Disabled } ;
2015-04-15 16:39:37 -07:00
2015-05-30 12:48:16 -07:00
public enum OpenMode { Viewing , Editing }
2015-04-15 16:59:12 -07:00
2015-05-30 12:48:16 -07:00
public enum WindowMode { Embeded , StandAlone } ;
2015-12-22 15:26:51 -08:00
2015-05-30 12:48:16 -07:00
private enum TraceInfoOpperation { DONT_COPY , DO_COPY } ;
2015-04-16 10:38:53 -07:00
2015-05-30 12:48:16 -07:00
public bool DisplayAllValueData { get ; set ; }
2014-12-20 11:12:02 -08:00
2015-05-30 12:48:16 -07:00
public bool HaveSelection
{
get { return MeshGroups . Count > 0 & & SelectedMeshGroupIndex > - 1 ; }
}
2014-12-20 23:45:13 -08:00
2015-05-30 12:48:16 -07:00
public List < MeshGroup > MeshGroups
{
get { return meshViewerWidget . MeshGroups ; }
2015-04-08 15:20:10 -07:00
}
2014-12-20 11:12:02 -08:00
2015-05-30 12:48:16 -07:00
public List < ScaleRotateTranslate > MeshGroupTransforms
2015-01-25 17:54:26 -08:00
{
2015-05-30 12:48:16 -07:00
get { return meshViewerWidget . MeshGroupTransforms ; }
}
public MeshGroup SelectedMeshGroup
{
get { return meshViewerWidget . SelectedMeshGroup ; }
}
public int SelectedMeshGroupIndex
{
get
2015-05-22 11:11:32 -07:00
{
2015-05-30 12:48:16 -07:00
return meshViewerWidget . SelectedMeshGroupIndex ;
2015-05-22 11:11:32 -07:00
}
2015-05-30 12:48:16 -07:00
set
2015-01-25 17:54:26 -08:00
{
2015-05-30 12:48:16 -07:00
if ( value ! = SelectedMeshGroupIndex )
2015-01-25 17:54:26 -08:00
{
2015-05-30 12:48:16 -07:00
meshViewerWidget . SelectedMeshGroupIndex = value ;
if ( SelectionChanged ! = null )
2015-01-25 17:54:26 -08:00
{
2015-05-30 12:48:16 -07:00
SelectionChanged ( this , null ) ;
2015-02-10 14:36:02 -08:00
}
2015-05-30 12:48:16 -07:00
Invalidate ( ) ;
2015-01-25 17:54:26 -08:00
}
}
2015-05-30 12:48:16 -07:00
}
2015-01-25 17:54:26 -08:00
2015-05-30 12:48:16 -07:00
public ScaleRotateTranslate SelectedMeshGroupTransform
{
get { return meshViewerWidget . SelectedMeshGroupTransform ; }
set { meshViewerWidget . SelectedMeshGroupTransform = value ; }
2015-01-25 17:54:26 -08:00
}
2015-05-30 12:48:16 -07:00
public WindowMode windowType { get ; set ; }
private bool DoAddFileAfterCreatingEditData { get ; set ; }
2015-12-22 15:26:51 -08:00
2015-05-30 12:48:16 -07:00
public override void OnClosed ( EventArgs e )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( unregisterEvents ! = null )
2014-10-10 14:52:50 -07:00
{
2015-05-30 12:48:16 -07:00
unregisterEvents ( this , null ) ;
2014-10-10 14:52:50 -07:00
}
2015-05-30 12:48:16 -07:00
base . OnClosed ( e ) ;
2014-10-10 14:52:50 -07:00
}
2015-05-30 12:48:16 -07:00
public override void OnDragDrop ( FileDropEventArgs fileDropEventArgs )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( AllowDragDrop ( ) )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
pendingPartsToLoad . Clear ( ) ;
foreach ( string droppedFileName in fileDropEventArgs . DroppedFiles )
2015-04-15 16:59:12 -07:00
{
2015-05-30 12:48:16 -07:00
string extension = Path . GetExtension ( droppedFileName ) . ToLower ( ) ;
2015-08-03 16:46:57 -07:00
if ( extension ! = "" & & ApplicationSettings . OpenDesignFileParams . Contains ( extension ) )
2015-05-30 12:48:16 -07:00
{
pendingPartsToLoad . Add ( droppedFileName ) ;
}
}
if ( pendingPartsToLoad . Count > 0 )
{
bool enterEditModeBeforeAddingParts = enterEditButtonsContainer . Visible = = true ;
if ( enterEditModeBeforeAddingParts )
{
EnterEditAndCreateSelectionData ( ) ;
}
else
{
LoadAndAddPartsToPlate ( pendingPartsToLoad . ToArray ( ) ) ;
}
2015-04-15 16:59:12 -07:00
}
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
base . OnDragDrop ( fileDropEventArgs ) ;
2015-04-08 15:20:10 -07:00
}
2014-10-12 20:40:38 -07:00
2015-05-30 12:48:16 -07:00
public override void OnDragEnter ( FileDropEventArgs fileDropEventArgs )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( AllowDragDrop ( ) )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
foreach ( string file in fileDropEventArgs . DroppedFiles )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
string extension = Path . GetExtension ( file ) . ToLower ( ) ;
2015-08-03 16:46:57 -07:00
if ( extension ! = "" & & ApplicationSettings . OpenDesignFileParams . Contains ( extension ) )
2015-05-30 12:48:16 -07:00
{
fileDropEventArgs . AcceptDrop = true ;
}
}
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
base . OnDragEnter ( fileDropEventArgs ) ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
public override void OnDragOver ( FileDropEventArgs fileDropEventArgs )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( AllowDragDrop ( ) )
{
foreach ( string file in fileDropEventArgs . DroppedFiles )
{
string extension = Path . GetExtension ( file ) . ToLower ( ) ;
2015-08-03 16:46:57 -07:00
if ( extension ! = "" & & ApplicationSettings . OpenDesignFileParams . Contains ( extension ) )
2015-05-30 12:48:16 -07:00
{
fileDropEventArgs . AcceptDrop = true ;
}
}
}
base . OnDragOver ( fileDropEventArgs ) ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
public override void OnDraw ( Graphics2D graphics2D )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( firstDraw )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
ClearBedAndLoadPrintItemWrapper ( printItemWrapper ) ;
firstDraw = false ;
}
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
if ( HaveSelection )
{
upArrow . SetPosition ( ) ;
heightDisplay . SetPosition ( ) ;
2015-04-08 15:20:10 -07:00
}
2014-03-20 18:20:52 -07:00
2015-05-30 12:48:16 -07:00
hasDrawn = true ;
base . OnDraw ( graphics2D ) ;
DrawStuffForSelectedPart ( graphics2D ) ;
}
2015-04-08 15:20:10 -07:00
2015-12-22 15:26:51 -08:00
private ViewControls3DButtons ? activeButtonBeforeMouseOverride = null ;
private ViewControls3DButtons ? activeButtonBeforeKeyOverride = null ;
2015-05-29 15:13:56 -07:00
public override void OnKeyDown ( KeyEventArgs keyEvent )
{
if ( activeButtonBeforeKeyOverride = = null )
{
activeButtonBeforeKeyOverride = viewControls3D . ActiveButton ;
if ( keyEvent . Alt )
{
viewControls3D . ActiveButton = ViewControls3DButtons . Rotate ;
}
else if ( keyEvent . Shift )
{
viewControls3D . ActiveButton = ViewControls3DButtons . Translate ;
}
else if ( keyEvent . Control )
{
viewControls3D . ActiveButton = ViewControls3DButtons . Scale ;
}
}
base . OnKeyDown ( keyEvent ) ;
}
public override void OnKeyUp ( KeyEventArgs keyEvent )
{
if ( activeButtonBeforeKeyOverride ! = null )
{
viewControls3D . ActiveButton = ( ViewControls3DButtons ) activeButtonBeforeKeyOverride ;
activeButtonBeforeKeyOverride = null ;
}
base . OnKeyUp ( keyEvent ) ;
}
2015-05-30 12:48:16 -07:00
public override void OnMouseDown ( MouseEventArgs mouseEvent )
2015-04-08 15:20:10 -07:00
{
2015-05-29 15:13:56 -07:00
// Show transform override
if ( activeButtonBeforeMouseOverride = = null & & mouseEvent . Button = = MouseButtons . Right )
{
activeButtonBeforeMouseOverride = viewControls3D . ActiveButton ;
viewControls3D . ActiveButton = ViewControls3DButtons . Rotate ;
}
else if ( activeButtonBeforeMouseOverride = = null & & mouseEvent . Button = = MouseButtons . Middle )
{
activeButtonBeforeMouseOverride = viewControls3D . ActiveButton ;
viewControls3D . ActiveButton = ViewControls3DButtons . Translate ;
}
2015-05-30 12:48:16 -07:00
autoRotating = false ;
base . OnMouseDown ( mouseEvent ) ;
if ( meshViewerWidget . TrackballTumbleWidget . UnderMouseState = = Agg . UI . UnderMouseState . FirstUnderMouse )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( meshViewerWidget . TrackballTumbleWidget . TransformState = = TrackBallController . MouseDownType . None
& & mouseEvent . Button = = MouseButtons . Left
& & ModifierKeys ! = Keys . Shift
& & ModifierKeys ! = Keys . Control
& & ModifierKeys ! = Keys . Alt )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( ! meshViewerWidget . MouseDownOnInteractionVolume )
{
int meshGroupHitIndex ;
if ( FindMeshGroupHitPosition ( mouseEvent . Position , out meshGroupHitIndex ) )
{
meshSelectInfo . hitPlane = new PlaneShape ( Vector3 . UnitZ , meshSelectInfo . planeDownHitPos . z , null ) ;
SelectedMeshGroupIndex = meshGroupHitIndex ;
2014-03-20 18:20:52 -07:00
2015-05-30 12:48:16 -07:00
transformOnMouseDown = SelectedMeshGroupTransform . translation ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
Invalidate ( ) ;
meshSelectInfo . downOnPart = true ;
}
else
{
SelectedMeshGroupIndex = - 1 ;
}
UpdateSizeInfo ( ) ;
}
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
}
}
2015-02-27 11:09:37 -08:00
2015-05-30 12:48:16 -07:00
public override void OnMouseMove ( MouseEventArgs mouseEvent )
{
if ( meshViewerWidget . TrackballTumbleWidget . TransformState = = TrackBallController . MouseDownType . None & & meshSelectInfo . downOnPart )
{
Vector2 meshViewerWidgetScreenPosition = meshViewerWidget . TransformFromParentSpace ( this , new Vector2 ( mouseEvent . X , mouseEvent . Y ) ) ;
Ray ray = meshViewerWidget . TrackballTumbleWidget . GetRayFromScreen ( meshViewerWidgetScreenPosition ) ;
IntersectInfo info = meshSelectInfo . hitPlane . GetClosestIntersection ( ray ) ;
if ( info ! = null )
2015-02-27 11:09:37 -08:00
{
2015-05-30 12:48:16 -07:00
Vector3 delta = info . hitPosition - meshSelectInfo . planeDownHitPos ;
2015-02-27 11:09:37 -08:00
2015-05-30 12:48:16 -07:00
Matrix4X4 totalTransform = Matrix4X4 . CreateTranslation ( new Vector3 ( - meshSelectInfo . lastMoveDelta ) ) ;
totalTransform * = Matrix4X4 . CreateTranslation ( new Vector3 ( delta ) ) ;
meshSelectInfo . lastMoveDelta = delta ;
2015-02-27 11:09:37 -08:00
2015-05-30 12:48:16 -07:00
ScaleRotateTranslate translated = SelectedMeshGroupTransform ;
translated . translation * = totalTransform ;
SelectedMeshGroupTransform = translated ;
2015-02-27 11:09:37 -08:00
2015-05-30 12:48:16 -07:00
Invalidate ( ) ;
2015-02-27 11:09:37 -08:00
}
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
base . OnMouseMove ( mouseEvent ) ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
public override void OnMouseUp ( MouseEventArgs mouseEvent )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( meshViewerWidget . TrackballTumbleWidget . TransformState = = TrackBallController . MouseDownType . None
& & meshSelectInfo . downOnPart
& & meshSelectInfo . lastMoveDelta ! = Vector3 . Zero )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
PartHasBeenChanged ( ) ;
}
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
meshSelectInfo . downOnPart = false ;
2015-04-08 15:20:10 -07:00
2015-05-29 15:13:56 -07:00
if ( activeButtonBeforeMouseOverride ! = null )
{
viewControls3D . ActiveButton = ( ViewControls3DButtons ) activeButtonBeforeMouseOverride ;
activeButtonBeforeMouseOverride = null ;
}
2015-05-30 12:48:16 -07:00
base . OnMouseUp ( mouseEvent ) ;
}
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
public void PartHasBeenChanged ( )
{
saveButtons . Visible = true ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
public void ThemeChanged ( object sender , EventArgs e )
{
2015-07-14 13:38:22 -07:00
processingProgressControl . FillColor = ActiveTheme . Instance . PrimaryAccentColor ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
MeshViewerWidget . SetMaterialColor ( 1 , ActiveTheme . Instance . PrimaryAccentColor ) ;
}
private void AddHandlers ( )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
expandViewOptions . CheckedStateChanged + = expandViewOptions_CheckedStateChanged ;
expandMirrorOptions . CheckedStateChanged + = expandMirrorOptions_CheckedStateChanged ;
if ( expandMaterialOptions ! = null )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
expandMaterialOptions . CheckedStateChanged + = expandMaterialOptions_CheckedStateChanged ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
expandRotateOptions . CheckedStateChanged + = expandRotateOptions_CheckedStateChanged ;
expandScaleOptions . CheckedStateChanged + = expandScaleOptions_CheckedStateChanged ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
SelectionChanged + = SetApplyScaleVisability ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
private void AddMaterialControls ( FlowLayoutWidget buttonPanel )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
extruderButtons . Clear ( ) ;
for ( int extruderIndex = 0 ; extruderIndex < ActiveSliceSettings . Instance . ExtruderCount ; extruderIndex + + )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
FlowLayoutWidget colorSelectionContainer = new FlowLayoutWidget ( FlowDirection . LeftToRight ) ;
colorSelectionContainer . HAnchor = HAnchor . ParentLeftRight ;
colorSelectionContainer . Padding = new BorderDouble ( 5 ) ;
2015-09-21 16:53:40 -07:00
string colorLabelText = "Material {0}" . Localize ( ) . FormatWith ( extruderIndex + 1 ) ;
2015-05-30 12:48:16 -07:00
RadioButton extruderSelection = new RadioButton ( colorLabelText , textColor : ActiveTheme . Instance . PrimaryTextColor ) ;
extruderButtons . Add ( extruderSelection ) ;
extruderSelection . SiblingRadioButtonList = extruderButtons ;
colorSelectionContainer . AddChild ( extruderSelection ) ;
colorSelectionContainer . AddChild ( new HorizontalSpacer ( ) ) ;
int extruderIndexLocal = extruderIndex ;
extruderSelection . Click + = ( sender , e ) = >
2015-02-05 16:14:30 -08:00
{
2015-05-30 12:48:16 -07:00
if ( SelectedMeshGroupIndex ! = - 1 )
2015-02-05 16:14:30 -08:00
{
2015-05-30 12:48:16 -07:00
foreach ( Mesh mesh in SelectedMeshGroup . Meshes )
2015-02-05 16:14:30 -08:00
{
2015-05-30 12:48:16 -07:00
MeshMaterialData material = MeshMaterialData . Get ( mesh ) ;
if ( material . MaterialIndex ! = extruderIndexLocal + 1 )
2015-02-05 16:14:30 -08:00
{
2015-05-30 12:48:16 -07:00
material . MaterialIndex = extruderIndexLocal + 1 ;
PartHasBeenChanged ( ) ;
2015-02-05 16:14:30 -08:00
}
}
}
2015-05-30 12:48:16 -07:00
} ;
2014-10-24 17:27:38 -07:00
2015-05-30 12:48:16 -07:00
this . SelectionChanged + = ( sender , e ) = >
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( SelectedMeshGroup ! = null )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
Mesh mesh = SelectedMeshGroup . Meshes [ 0 ] ;
MeshMaterialData material = MeshMaterialData . Get ( mesh ) ;
2014-01-29 19:09:30 -08:00
2015-05-30 12:48:16 -07:00
for ( int i = 0 ; i < extruderButtons . Count ; i + + )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( material . MaterialIndex - 1 = = i )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
( ( RadioButton ) extruderButtons [ i ] ) . Checked = true ;
2015-04-08 15:20:10 -07:00
}
}
}
2015-05-30 12:48:16 -07:00
} ;
2014-10-13 19:29:25 -07:00
2015-05-30 12:48:16 -07:00
buttonPanel . AddChild ( colorSelectionContainer ) ;
2015-04-08 15:20:10 -07:00
}
}
2014-09-26 15:04:04 -07:00
2015-05-30 12:48:16 -07:00
private void AddMirrorControls ( FlowLayoutWidget buttonPanel )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
List < GuiWidget > mirrorControls = new List < GuiWidget > ( ) ;
transformControls . Add ( "Mirror" , mirrorControls ) ;
2014-09-26 15:04:04 -07:00
2015-05-30 12:48:16 -07:00
textImageButtonFactory . FixedWidth = EditButtonHeight ;
2014-09-26 15:04:04 -07:00
2015-05-30 12:48:16 -07:00
FlowLayoutWidget buttonContainer = new FlowLayoutWidget ( FlowDirection . LeftToRight ) ;
buttonContainer . HAnchor = HAnchor . ParentLeftRight ;
Button mirrorXButton = textImageButtonFactory . Generate ( "X" , centerText : true ) ;
buttonContainer . AddChild ( mirrorXButton ) ;
mirrorControls . Add ( mirrorXButton ) ;
mirrorXButton . Click + = ( object sender , EventArgs mouseEvent ) = >
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( SelectedMeshGroupIndex ! = - 1 )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
SelectedMeshGroup . ReverseFaceEdges ( ) ;
ScaleRotateTranslate scale = SelectedMeshGroupTransform ;
scale . scale * = Matrix4X4 . CreateScale ( - 1 , 1 , 1 ) ;
SelectedMeshGroupTransform = scale ;
PlatingHelper . PlaceMeshGroupOnBed ( MeshGroups , MeshGroupTransforms , SelectedMeshGroupIndex ) ;
PartHasBeenChanged ( ) ;
Invalidate ( ) ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
} ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
Button mirrorYButton = textImageButtonFactory . Generate ( "Y" , centerText : true ) ;
buttonContainer . AddChild ( mirrorYButton ) ;
mirrorControls . Add ( mirrorYButton ) ;
mirrorYButton . Click + = ( object sender , EventArgs mouseEvent ) = >
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( SelectedMeshGroupIndex ! = - 1 )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
SelectedMeshGroup . ReverseFaceEdges ( ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
ScaleRotateTranslate scale = SelectedMeshGroupTransform ;
scale . scale * = Matrix4X4 . CreateScale ( 1 , - 1 , 1 ) ;
SelectedMeshGroupTransform = scale ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
PlatingHelper . PlaceMeshGroupOnBed ( MeshGroups , MeshGroupTransforms , SelectedMeshGroupIndex ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
PartHasBeenChanged ( ) ;
Invalidate ( ) ;
}
} ;
Button mirrorZButton = textImageButtonFactory . Generate ( "Z" , centerText : true ) ;
buttonContainer . AddChild ( mirrorZButton ) ;
mirrorControls . Add ( mirrorZButton ) ;
mirrorZButton . Click + = ( object sender , EventArgs mouseEvent ) = >
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( SelectedMeshGroupIndex ! = - 1 )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
SelectedMeshGroup . ReverseFaceEdges ( ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
ScaleRotateTranslate scale = SelectedMeshGroupTransform ;
scale . scale * = Matrix4X4 . CreateScale ( 1 , 1 , - 1 ) ;
SelectedMeshGroupTransform = scale ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
PlatingHelper . PlaceMeshGroupOnBed ( MeshGroups , MeshGroupTransforms , SelectedMeshGroupIndex ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
PartHasBeenChanged ( ) ;
Invalidate ( ) ;
}
} ;
buttonPanel . AddChild ( buttonContainer ) ;
buttonPanel . AddChild ( generateHorizontalRule ( ) ) ;
textImageButtonFactory . FixedWidth = 0 ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
private void AddRotateControls ( FlowLayoutWidget buttonPanel )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
List < GuiWidget > rotateControls = new List < GuiWidget > ( ) ;
transformControls . Add ( "Rotate" . Localize ( ) , rotateControls ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
textImageButtonFactory . FixedWidth = EditButtonHeight ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
FlowLayoutWidget degreesContainer = new FlowLayoutWidget ( FlowDirection . LeftToRight ) ;
degreesContainer . HAnchor = HAnchor . ParentLeftRight ;
degreesContainer . Padding = new BorderDouble ( 5 ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
string degreesLabelText = "Degrees" . Localize ( ) ;
string degreesLabelTextFull = "{0}:" . FormatWith ( degreesLabelText ) ;
TextWidget degreesLabel = new TextWidget ( degreesLabelText , textColor : ActiveTheme . Instance . PrimaryTextColor ) ;
degreesContainer . AddChild ( degreesLabel ) ;
degreesContainer . AddChild ( new HorizontalSpacer ( ) ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
MHNumberEdit degreesControl = new MHNumberEdit ( 45 , pixelWidth : 40 , allowNegatives : true , allowDecimals : true , increment : 5 , minValue : - 360 , maxValue : 360 ) ;
degreesControl . VAnchor = Agg . UI . VAnchor . ParentTop ;
degreesContainer . AddChild ( degreesControl ) ;
rotateControls . Add ( degreesControl ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
buttonPanel . AddChild ( degreesContainer ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
FlowLayoutWidget rotateButtonContainer = new FlowLayoutWidget ( FlowDirection . LeftToRight ) ;
rotateButtonContainer . HAnchor = HAnchor . ParentLeftRight ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
Button rotateXButton = textImageButtonFactory . Generate ( "" , "icon_rotate_32x32.png" ) ;
TextWidget centeredX = new TextWidget ( "X" , pointSize : 10 , textColor : ActiveTheme . Instance . PrimaryTextColor ) ; centeredX . Margin = new BorderDouble ( 3 , 0 , 0 , 0 ) ; centeredX . AnchorCenter ( ) ; rotateXButton . AddChild ( centeredX ) ;
rotateButtonContainer . AddChild ( rotateXButton ) ;
rotateControls . Add ( rotateXButton ) ;
rotateXButton . Click + = ( object sender , EventArgs mouseEvent ) = >
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( SelectedMeshGroupIndex ! = - 1 )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
double radians = MathHelper . DegreesToRadians ( degreesControl . ActuallNumberEdit . Value ) ;
// rotate it
ScaleRotateTranslate rotated = SelectedMeshGroupTransform ;
rotated . rotation * = Matrix4X4 . CreateRotationX ( radians ) ;
SelectedMeshGroupTransform = rotated ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
PlatingHelper . PlaceMeshGroupOnBed ( MeshGroups , MeshGroupTransforms , SelectedMeshGroupIndex ) ;
PartHasBeenChanged ( ) ;
Invalidate ( ) ;
}
} ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
Button rotateYButton = textImageButtonFactory . Generate ( "" , "icon_rotate_32x32.png" ) ;
TextWidget centeredY = new TextWidget ( "Y" , pointSize : 10 , textColor : ActiveTheme . Instance . PrimaryTextColor ) ; centeredY . Margin = new BorderDouble ( 3 , 0 , 0 , 0 ) ; centeredY . AnchorCenter ( ) ; rotateYButton . AddChild ( centeredY ) ;
rotateButtonContainer . AddChild ( rotateYButton ) ;
rotateControls . Add ( rotateYButton ) ;
rotateYButton . Click + = ( object sender , EventArgs mouseEvent ) = >
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( SelectedMeshGroupIndex ! = - 1 )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
double radians = MathHelper . DegreesToRadians ( degreesControl . ActuallNumberEdit . Value ) ;
// rotate it
ScaleRotateTranslate rotated = SelectedMeshGroupTransform ;
rotated . rotation * = Matrix4X4 . CreateRotationY ( radians ) ;
SelectedMeshGroupTransform = rotated ;
PlatingHelper . PlaceMeshGroupOnBed ( MeshGroups , MeshGroupTransforms , SelectedMeshGroupIndex ) ;
saveButtons . Visible = true ;
Invalidate ( ) ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
} ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
Button rotateZButton = textImageButtonFactory . Generate ( "" , "icon_rotate_32x32.png" ) ;
TextWidget centeredZ = new TextWidget ( "Z" , pointSize : 10 , textColor : ActiveTheme . Instance . PrimaryTextColor ) ; centeredZ . Margin = new BorderDouble ( 3 , 0 , 0 , 0 ) ; centeredZ . AnchorCenter ( ) ; rotateZButton . AddChild ( centeredZ ) ;
rotateButtonContainer . AddChild ( rotateZButton ) ;
rotateControls . Add ( rotateZButton ) ;
rotateZButton . Click + = ( object sender , EventArgs mouseEvent ) = >
{
if ( SelectedMeshGroupIndex ! = - 1 )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
double radians = MathHelper . DegreesToRadians ( degreesControl . ActuallNumberEdit . Value ) ;
// rotate it
ScaleRotateTranslate rotated = SelectedMeshGroupTransform ;
rotated . rotation * = Matrix4X4 . CreateRotationZ ( radians ) ;
SelectedMeshGroupTransform = rotated ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
PlatingHelper . PlaceMeshGroupOnBed ( MeshGroups , MeshGroupTransforms , SelectedMeshGroupIndex ) ;
PartHasBeenChanged ( ) ;
Invalidate ( ) ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
} ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
buttonPanel . AddChild ( rotateButtonContainer ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
Button layFlatButton = whiteButtonFactory . Generate ( "Align to Bed" . Localize ( ) , centerText : true ) ;
layFlatButton . Cursor = Cursors . Hand ;
buttonPanel . AddChild ( layFlatButton ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
layFlatButton . Click + = ( object sender , EventArgs mouseEvent ) = >
{
if ( SelectedMeshGroupIndex ! = - 1 )
{
MakeLowestFaceFlat ( SelectedMeshGroupIndex ) ;
2014-01-29 19:09:30 -08:00
2015-05-30 12:48:16 -07:00
PartHasBeenChanged ( ) ;
Invalidate ( ) ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
} ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
buttonPanel . AddChild ( generateHorizontalRule ( ) ) ;
textImageButtonFactory . FixedWidth = 0 ;
2015-04-08 15:20:10 -07:00
}
private void AddSaveAndSaveAs ( FlowLayoutWidget flowToAddTo )
{
TupleList < string , Func < bool > > buttonList = new TupleList < string , Func < bool > > ( ) ;
buttonList . Add ( "Save" , ( ) = >
{
MergeAndSavePartsToCurrentMeshFile ( ) ;
return true ;
} ) ;
2015-12-22 15:26:51 -08:00
2015-04-08 15:20:10 -07:00
buttonList . Add ( "Save As" , ( ) = >
{
2015-01-26 16:49:21 -08:00
UiThread . RunOnIdle ( OpenSaveAsWindow ) ;
2015-04-08 15:20:10 -07:00
return true ;
} ) ;
2015-08-10 13:36:31 -07:00
2015-04-08 15:20:10 -07:00
SplitButtonFactory splitButtonFactory = new SplitButtonFactory ( ) ;
2015-01-27 09:34:15 -08:00
splitButtonFactory . FixedHeight = 40 * TextWidget . GlobalPointSizeScaleRatio ;
2015-04-08 15:20:10 -07:00
saveButtons = splitButtonFactory . Generate ( buttonList , Direction . Up , imageName : "icon_save_32x32.png" ) ;
saveButtons . Visible = false ;
2014-12-12 12:57:44 -08:00
2015-04-08 15:20:10 -07:00
saveButtons . Margin = new BorderDouble ( ) ;
saveButtons . VAnchor | = VAnchor . ParentCenter ;
2014-12-12 12:57:44 -08:00
2015-04-08 15:20:10 -07:00
flowToAddTo . AddChild ( saveButtons ) ;
}
2014-11-17 15:50:39 -08:00
2015-04-08 15:20:10 -07:00
private void AddScaleControls ( FlowLayoutWidget buttonPanel )
{
List < GuiWidget > scaleControls = new List < GuiWidget > ( ) ;
transformControls . Add ( "Scale" , scaleControls ) ;
2014-05-08 11:30:56 -07:00
2015-04-08 15:20:10 -07:00
// Put in the scale ratio edit field
{
FlowLayoutWidget scaleRatioContainer = new FlowLayoutWidget ( FlowDirection . LeftToRight ) ;
scaleRatioContainer . HAnchor = HAnchor . ParentLeftRight ;
scaleRatioContainer . Padding = new BorderDouble ( 5 ) ;
string scaleRatioLabelText = "Ratio" . Localize ( ) ;
string scaleRatioLabelTextFull = "{0}:" . FormatWith ( scaleRatioLabelText ) ;
TextWidget scaleRatioLabel = new TextWidget ( scaleRatioLabelTextFull , textColor : ActiveTheme . Instance . PrimaryTextColor ) ;
scaleRatioLabel . Margin = new BorderDouble ( 0 , 0 , 3 , 0 ) ;
scaleRatioLabel . VAnchor = VAnchor . ParentCenter ;
scaleRatioContainer . AddChild ( scaleRatioLabel ) ;
scaleRatioContainer . AddChild ( new HorizontalSpacer ( ) ) ;
2015-04-16 10:59:07 -07:00
scaleRatioControl = new MHNumberEdit ( 1 , pixelWidth : 50 * TextWidget . GlobalPointSizeScaleRatio , allowDecimals : true , increment : . 05 ) ;
2015-04-08 15:20:10 -07:00
scaleRatioControl . SelectAllOnFocus = true ;
scaleRatioControl . VAnchor = VAnchor . ParentCenter ;
scaleRatioContainer . AddChild ( scaleRatioControl ) ;
scaleRatioControl . ActuallNumberEdit . KeyPressed + = ( sender , e ) = >
{
SetApplyScaleVisability ( this , null ) ;
} ;
2014-01-29 19:09:30 -08:00
2015-04-08 15:20:10 -07:00
scaleRatioControl . ActuallNumberEdit . KeyDown + = ( sender , e ) = >
{
SetApplyScaleVisability ( this , null ) ;
} ;
2014-03-31 17:08:27 -07:00
2015-04-08 15:20:10 -07:00
scaleRatioControl . ActuallNumberEdit . EnterPressed + = ( object sender , KeyEventArgs keyEvent ) = >
{
ApplyScaleFromEditField ( ) ;
} ;
2014-03-31 17:08:27 -07:00
2015-04-08 15:20:10 -07:00
scaleRatioContainer . AddChild ( CreateScaleDropDownMenu ( ) ) ;
2014-03-31 17:08:27 -07:00
2015-04-08 15:20:10 -07:00
buttonPanel . AddChild ( scaleRatioContainer ) ;
2014-05-06 11:22:48 -07:00
2015-04-08 15:20:10 -07:00
scaleControls . Add ( scaleRatioControl ) ;
}
2014-10-12 20:40:38 -07:00
2015-04-08 15:20:10 -07:00
applyScaleButton = whiteButtonFactory . Generate ( "Apply Scale" . Localize ( ) , centerText : true ) ;
applyScaleButton . Visible = false ;
applyScaleButton . Cursor = Cursors . Hand ;
buttonPanel . AddChild ( applyScaleButton ) ;
2014-05-07 18:34:27 -07:00
2015-04-08 15:20:10 -07:00
scaleControls . Add ( applyScaleButton ) ;
applyScaleButton . Click + = ( object sender , EventArgs mouseEvent ) = >
{
ApplyScaleFromEditField ( ) ;
} ;
2014-05-06 11:22:48 -07:00
2015-04-08 15:20:10 -07:00
// add in the dimensions
{
buttonPanel . AddChild ( createAxisScalingControl ( "x" , 0 ) ) ;
buttonPanel . AddChild ( createAxisScalingControl ( "y" , 1 ) ) ;
buttonPanel . AddChild ( createAxisScalingControl ( "z" , 2 ) ) ;
2014-03-31 17:08:27 -07:00
2015-04-08 15:20:10 -07:00
uniformScale = new CheckBox ( "Lock Ratio" . Localize ( ) , textColor : ActiveTheme . Instance . PrimaryTextColor ) ;
uniformScale . Checked = true ;
2014-05-06 11:22:48 -07:00
2015-04-08 15:20:10 -07:00
FlowLayoutWidget leftToRight = new FlowLayoutWidget ( ) ;
leftToRight . Padding = new BorderDouble ( 5 , 3 ) ;
2014-05-06 11:22:48 -07:00
2015-04-08 15:20:10 -07:00
leftToRight . AddChild ( uniformScale ) ;
buttonPanel . AddChild ( leftToRight ) ;
}
buttonPanel . AddChild ( generateHorizontalRule ( ) ) ;
}
2015-05-30 12:48:16 -07:00
private bool AllowDragDrop ( )
{
2015-07-13 10:08:08 -07:00
if ( ( ! enterEditButtonsContainer . Visible
2015-05-30 12:48:16 -07:00
& & ! doEdittingButtonsContainer . Visible )
2015-12-22 15:26:51 -08:00
| | printItemWrapper = = null | | printItemWrapper . PrintItem . ReadOnly )
2015-05-30 12:48:16 -07:00
{
return false ;
}
return true ;
}
private void ApplyScaleFromEditField ( )
{
if ( HaveSelection )
{
double scale = scaleRatioControl . ActuallNumberEdit . Value ;
if ( scale > 0 )
{
ScaleAxis ( scale , 0 ) ;
ScaleAxis ( scale , 1 ) ;
ScaleAxis ( scale , 2 ) ;
}
}
}
2015-06-11 12:06:40 -07:00
private void AutoSpin ( )
2015-05-30 12:48:16 -07:00
{
if ( ! WidgetHasBeenClosed & & autoRotating )
{
// add it back in to keep it running.
UiThread . RunOnIdle ( AutoSpin , . 04 ) ;
if ( ( ! timeSinceLastSpin . IsRunning | | timeSinceLastSpin . ElapsedMilliseconds > 50 )
& & hasDrawn )
{
hasDrawn = false ;
timeSinceLastSpin . Restart ( ) ;
Quaternion currentRotation = meshViewerWidget . TrackballTumbleWidget . TrackBallController . CurrentRotation . GetRotation ( ) ;
Quaternion invertedRotation = Quaternion . Invert ( currentRotation ) ;
Quaternion rotateAboutZ = Quaternion . FromEulerAngles ( new Vector3 ( 0 , 0 , . 01 ) ) ;
rotateAboutZ = invertedRotation * rotateAboutZ * currentRotation ;
meshViewerWidget . TrackballTumbleWidget . TrackBallController . Rotate ( rotateAboutZ ) ;
Invalidate ( ) ;
}
}
}
2015-07-02 11:23:44 -07:00
private void ReportProgressChanged ( double progress0To1 , string processingState , out bool continueProcessing )
2015-05-30 12:48:16 -07:00
{
if ( ! timeSinceReported . IsRunning | | timeSinceReported . ElapsedMilliseconds > 100
| | processingState ! = processingProgressControl . ProgressMessage )
{
2015-06-11 12:06:40 -07:00
UiThread . RunOnIdle ( ( ) = >
2015-05-30 12:48:16 -07:00
{
2015-07-14 13:38:22 -07:00
processingProgressControl . RatioComplete = progress0To1 ;
2015-05-30 12:48:16 -07:00
processingProgressControl . ProgressMessage = processingState ;
} ) ;
timeSinceReported . Restart ( ) ;
}
continueProcessing = true ;
}
private void ClearBedAndLoadPrintItemWrapper ( PrintItemWrapper printItemWrapper )
{
SwitchStateToNotEditing ( ) ;
MeshGroups . Clear ( ) ;
MeshGroupExtraData . Clear ( ) ;
MeshGroupTransforms . Clear ( ) ;
if ( printItemWrapper ! = null )
{
// remove it first to make sure we don't double add it
2015-09-23 13:33:14 -07:00
PrintItemWrapper . FileHasChanged . UnregisterEvent ( ReloadMeshIfChangeExternaly , ref unregisterEvents ) ;
PrintItemWrapper . FileHasChanged . RegisterEvent ( ReloadMeshIfChangeExternaly , ref unregisterEvents ) ; ;
2015-05-30 12:48:16 -07:00
// don't load the mesh until we get all the rest of the interface built
meshViewerWidget . LoadDone + = new EventHandler ( meshViewerWidget_LoadDone ) ;
2015-08-10 15:35:56 -07:00
Vector2 bedCenter = new Vector2 ( ) ;
MeshViewerWidget . CenterPartAfterLoad doCentering = MeshViewerWidget . CenterPartAfterLoad . DONT ;
2015-12-22 15:26:51 -08:00
if ( ActiveSliceSettings . Instance ! = null
2015-08-10 15:35:56 -07:00
& & ActiveSliceSettings . Instance . CenterOnBed ( ) )
{
doCentering = MeshViewerWidget . CenterPartAfterLoad . DO ;
bedCenter = ActiveSliceSettings . Instance . BedCenter ;
}
meshViewerWidget . LoadMesh ( printItemWrapper . FileLocation , doCentering , bedCenter ) ;
2015-05-30 12:48:16 -07:00
}
partHasBeenEdited = false ;
}
2015-04-08 15:20:10 -07:00
private GuiWidget createAxisScalingControl ( string axis , int axisIndex )
{
FlowLayoutWidget leftToRight = new FlowLayoutWidget ( ) ;
leftToRight . Padding = new BorderDouble ( 5 , 3 ) ;
TextWidget sizeDescription = new TextWidget ( "{0}:" . FormatWith ( axis ) , textColor : ActiveTheme . Instance . PrimaryTextColor ) ;
sizeDescription . VAnchor = Agg . UI . VAnchor . ParentCenter ;
leftToRight . AddChild ( sizeDescription ) ;
sizeDisplay [ axisIndex ] = new EditableNumberDisplay ( textImageButtonFactory , "100" , "1000.00" ) ;
sizeDisplay [ axisIndex ] . EditComplete + = ( sender , e ) = >
{
if ( HaveSelection )
{
SetNewModelSize ( sizeDisplay [ axisIndex ] . GetValue ( ) , axisIndex ) ;
sizeDisplay [ axisIndex ] . SetDisplayString ( "{0:0.00}" . FormatWith ( SelectedMeshGroup . GetAxisAlignedBoundingBox ( ) . Size [ axisIndex ] ) ) ;
UpdateSizeInfo ( ) ;
}
else
{
sizeDisplay [ axisIndex ] . SetDisplayString ( "---" ) ;
}
} ;
leftToRight . AddChild ( sizeDisplay [ axisIndex ] ) ;
return leftToRight ;
}
2015-05-30 12:48:16 -07:00
private void CreateOptionsContent ( )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
AddRotateControls ( rotateOptionContainer ) ;
AddScaleControls ( scaleOptionContainer ) ;
}
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
private void CreateRenderTypeRadioButtons ( FlowLayoutWidget viewOptionContainer )
{
string renderTypeString = UserSettings . Instance . get ( "defaultRenderSetting" ) ;
if ( renderTypeString = = null )
{
if ( ActiveTheme . Instance . DisplayMode = = ActiveTheme . ApplicationDisplayType . Touchscreen )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
renderTypeString = "Shaded" ;
2015-04-08 15:20:10 -07:00
}
else
{
2015-05-30 12:48:16 -07:00
renderTypeString = "Outlines" ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
UserSettings . Instance . set ( "defaultRenderSetting" , renderTypeString ) ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
RenderOpenGl . RenderTypes renderType ;
bool canParse = Enum . TryParse < RenderOpenGl . RenderTypes > ( renderTypeString , out renderType ) ;
if ( canParse )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
meshViewerWidget . RenderType = renderType ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
RadioButton renderTypeShaded = new RadioButton ( "Shaded" . Localize ( ) , textColor : ActiveTheme . Instance . PrimaryTextColor ) ;
renderTypeShaded . Checked = ( meshViewerWidget . RenderType = = RenderTypes . Shaded ) ;
renderTypeShaded . CheckedStateChanged + = ( sender , e ) = >
{
meshViewerWidget . RenderType = RenderTypes . Shaded ;
UserSettings . Instance . set ( "defaultRenderSetting" , meshViewerWidget . RenderType . ToString ( ) ) ;
} ;
viewOptionContainer . AddChild ( renderTypeShaded ) ;
2015-04-08 15:20:10 -07:00
}
{
2015-05-30 12:48:16 -07:00
RadioButton renderTypeOutlines = new RadioButton ( "Outlines" . Localize ( ) , textColor : ActiveTheme . Instance . PrimaryTextColor ) ;
renderTypeOutlines . Checked = ( meshViewerWidget . RenderType = = RenderTypes . Outlines ) ;
renderTypeOutlines . CheckedStateChanged + = ( sender , e ) = >
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
meshViewerWidget . RenderType = RenderTypes . Outlines ;
UserSettings . Instance . set ( "defaultRenderSetting" , meshViewerWidget . RenderType . ToString ( ) ) ;
} ;
viewOptionContainer . AddChild ( renderTypeOutlines ) ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
{
RadioButton renderTypePolygons = new RadioButton ( "Polygons" . Localize ( ) , textColor : ActiveTheme . Instance . PrimaryTextColor ) ;
renderTypePolygons . Checked = ( meshViewerWidget . RenderType = = RenderTypes . Polygons ) ;
renderTypePolygons . CheckedStateChanged + = ( sender , e ) = >
{
meshViewerWidget . RenderType = RenderTypes . Polygons ;
UserSettings . Instance . set ( "defaultRenderSetting" , meshViewerWidget . RenderType . ToString ( ) ) ;
} ;
viewOptionContainer . AddChild ( renderTypePolygons ) ;
}
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
private FlowLayoutWidget CreateRightButtonPanel ( double buildHeight )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
FlowLayoutWidget buttonRightPanel = new FlowLayoutWidget ( FlowDirection . TopToBottom ) ;
buttonRightPanel . Width = 200 ;
{
BorderDouble buttonMargin = new BorderDouble ( top : 3 ) ;
2015-12-16 18:14:32 -08:00
expandRotateOptions = expandMenuOptionFactory . GenerateCheckBoxButton ( "Rotate" . Localize ( ) . ToUpper ( ) , "icon_arrow_right_no_border_32x32.png" , "icon_arrow_down_no_border_32x32.png" ) ;
2015-05-30 12:48:16 -07:00
expandRotateOptions . Margin = new BorderDouble ( bottom : 2 ) ;
buttonRightPanel . AddChild ( expandRotateOptions ) ;
rotateOptionContainer = new FlowLayoutWidget ( FlowDirection . TopToBottom ) ;
rotateOptionContainer . HAnchor = HAnchor . ParentLeftRight ;
rotateOptionContainer . Visible = false ;
buttonRightPanel . AddChild ( rotateOptionContainer ) ;
2015-12-16 18:14:32 -08:00
expandScaleOptions = expandMenuOptionFactory . GenerateCheckBoxButton ( "Scale" . Localize ( ) . ToUpper ( ) , "icon_arrow_right_no_border_32x32.png" , "icon_arrow_down_no_border_32x32.png" ) ;
2015-05-30 12:48:16 -07:00
expandScaleOptions . Margin = new BorderDouble ( bottom : 2 ) ;
buttonRightPanel . AddChild ( expandScaleOptions ) ;
scaleOptionContainer = new FlowLayoutWidget ( FlowDirection . TopToBottom ) ;
scaleOptionContainer . HAnchor = HAnchor . ParentLeftRight ;
scaleOptionContainer . Visible = false ;
buttonRightPanel . AddChild ( scaleOptionContainer ) ;
// put in the mirror options
{
2015-12-16 18:14:32 -08:00
expandMirrorOptions = expandMenuOptionFactory . GenerateCheckBoxButton ( "Mirror" . Localize ( ) . ToUpper ( ) , "icon_arrow_right_no_border_32x32.png" , "icon_arrow_down_no_border_32x32.png" ) ;
2015-05-30 12:48:16 -07:00
expandMirrorOptions . Margin = new BorderDouble ( bottom : 2 ) ;
buttonRightPanel . AddChild ( expandMirrorOptions ) ;
mirrorOptionContainer = new FlowLayoutWidget ( FlowDirection . TopToBottom ) ;
mirrorOptionContainer . HAnchor = HAnchor . ParentLeftRight ;
mirrorOptionContainer . Visible = false ;
buttonRightPanel . AddChild ( mirrorOptionContainer ) ;
AddMirrorControls ( mirrorOptionContainer ) ;
}
// put in the material options
int numberOfExtruders = ActiveSliceSettings . Instance . ExtruderCount ;
2015-12-16 18:14:32 -08:00
expandMaterialOptions = expandMenuOptionFactory . GenerateCheckBoxButton ( "Materials" . Localize ( ) . ToUpper ( ) , "icon_arrow_right_no_border_32x32.png" , "icon_arrow_down_no_border_32x32.png" ) ;
2015-05-30 12:48:16 -07:00
expandMaterialOptions . Margin = new BorderDouble ( bottom : 2 ) ;
if ( numberOfExtruders > 1 )
{
buttonRightPanel . AddChild ( expandMaterialOptions ) ;
materialOptionContainer = new FlowLayoutWidget ( FlowDirection . TopToBottom ) ;
materialOptionContainer . HAnchor = HAnchor . ParentLeftRight ;
materialOptionContainer . Visible = false ;
buttonRightPanel . AddChild ( materialOptionContainer ) ;
AddMaterialControls ( materialOptionContainer ) ;
}
// put in the view options
{
2015-12-16 18:14:32 -08:00
expandViewOptions = expandMenuOptionFactory . GenerateCheckBoxButton ( "Display" . Localize ( ) . ToUpper ( ) , "icon_arrow_right_no_border_32x32.png" , "icon_arrow_down_no_border_32x32.png" ) ;
2015-05-30 12:48:16 -07:00
expandViewOptions . Margin = new BorderDouble ( bottom : 2 ) ;
buttonRightPanel . AddChild ( expandViewOptions ) ;
viewOptionContainer = new FlowLayoutWidget ( FlowDirection . TopToBottom ) ;
viewOptionContainer . HAnchor = HAnchor . ParentLeftRight ;
viewOptionContainer . Padding = new BorderDouble ( left : 4 ) ;
viewOptionContainer . Visible = false ;
{
2015-12-16 18:14:32 -08:00
CheckBox showBedCheckBox = new CheckBox ( "Show Print Bed" . Localize ( ) , textColor : ActiveTheme . Instance . PrimaryTextColor ) ;
2015-05-30 12:48:16 -07:00
showBedCheckBox . Checked = true ;
showBedCheckBox . CheckedStateChanged + = ( sender , e ) = >
{
meshViewerWidget . RenderBed = showBedCheckBox . Checked ;
} ;
viewOptionContainer . AddChild ( showBedCheckBox ) ;
if ( buildHeight > 0 )
{
2015-12-16 18:14:32 -08:00
CheckBox showBuildVolumeCheckBox = new CheckBox ( "Show Print Area" . Localize ( ) , textColor : ActiveTheme . Instance . PrimaryTextColor ) ;
2015-05-30 12:48:16 -07:00
showBuildVolumeCheckBox . Checked = false ;
showBuildVolumeCheckBox . Margin = new BorderDouble ( bottom : 5 ) ;
showBuildVolumeCheckBox . CheckedStateChanged + = ( sender , e ) = >
{
meshViewerWidget . RenderBuildVolume = showBuildVolumeCheckBox . Checked ;
} ;
viewOptionContainer . AddChild ( showBuildVolumeCheckBox ) ;
}
if ( ActiveTheme . Instance . IsTouchScreen )
{
UserSettings . Instance . set ( "defaultRenderSetting" , RenderTypes . Shaded . ToString ( ) ) ;
}
else
{
CreateRenderTypeRadioButtons ( viewOptionContainer ) ;
}
}
buttonRightPanel . AddChild ( viewOptionContainer ) ;
}
GuiWidget verticalSpacer = new GuiWidget ( ) ;
verticalSpacer . VAnchor = VAnchor . ParentBottomTop ;
buttonRightPanel . AddChild ( verticalSpacer ) ;
}
buttonRightPanel . Padding = new BorderDouble ( 6 , 6 ) ;
buttonRightPanel . Margin = new BorderDouble ( 0 , 1 ) ;
buttonRightPanel . BackgroundColor = ActiveTheme . Instance . PrimaryBackgroundColor ;
buttonRightPanel . VAnchor = VAnchor . ParentBottomTop ;
return buttonRightPanel ;
}
private DropDownMenu CreateScaleDropDownMenu ( )
{
DropDownMenu presetScaleMenu = new DropDownMenu ( "" , Direction . Down ) ;
presetScaleMenu . NormalArrowColor = ActiveTheme . Instance . PrimaryTextColor ;
presetScaleMenu . HoverArrowColor = ActiveTheme . Instance . PrimaryTextColor ;
2015-04-08 15:20:10 -07:00
presetScaleMenu . MenuAsWideAsItems = false ;
presetScaleMenu . AlignToRightEdge = true ;
//presetScaleMenu.OpenOffset = new Vector2(-50, 0);
2015-05-18 17:29:05 -07:00
presetScaleMenu . HAnchor = HAnchor . AbsolutePosition ;
presetScaleMenu . VAnchor = VAnchor . AbsolutePosition ;
2015-04-08 15:20:10 -07:00
presetScaleMenu . Width = 25 ;
presetScaleMenu . Height = scaleRatioControl . Height + 2 ;
presetScaleMenu . AddItem ( "mm to in (.0393)" ) ;
presetScaleMenu . AddItem ( "in to mm (25.4)" ) ;
presetScaleMenu . AddItem ( "mm to cm (.1)" ) ;
presetScaleMenu . AddItem ( "cm to mm (10)" ) ;
string resetLable = "reset" . Localize ( ) ;
string resetLableFull = "{0} (1)" . FormatWith ( resetLable ) ;
presetScaleMenu . AddItem ( resetLableFull ) ;
presetScaleMenu . SelectionChanged + = ( sender , e ) = >
{
double scale = 1 ;
switch ( presetScaleMenu . SelectedIndex )
{
case 0 :
scale = 1.0 / 25.4 ;
break ;
case 1 :
scale = 25.4 ;
break ;
case 2 :
scale = . 1 ;
break ;
case 3 :
scale = 10 ;
break ;
case 4 :
scale = 1 ;
break ;
}
2014-11-24 22:24:30 -08:00
2015-04-08 15:20:10 -07:00
scaleRatioControl . ActuallNumberEdit . Value = scale ;
ApplyScaleFromEditField ( ) ;
} ;
return presetScaleMenu ;
}
2015-05-30 12:48:16 -07:00
private void DeleteSelectedMesh ( )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
// don't ever delete the last mesh
if ( SelectedMeshGroupIndex ! = - 1
& & MeshGroups . Count > 1 )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
MeshGroups . RemoveAt ( SelectedMeshGroupIndex ) ;
MeshGroupExtraData . RemoveAt ( SelectedMeshGroupIndex ) ;
MeshGroupTransforms . RemoveAt ( SelectedMeshGroupIndex ) ;
SelectedMeshGroupIndex = Math . Min ( SelectedMeshGroupIndex , MeshGroups . Count - 1 ) ;
PartHasBeenChanged ( ) ;
Invalidate ( ) ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
}
2014-01-29 19:09:30 -08:00
2015-05-30 12:48:16 -07:00
private void DrawStuffForSelectedPart ( Graphics2D graphics2D )
{
if ( SelectedMeshGroup ! = null )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
AxisAlignedBoundingBox selectedBounds = SelectedMeshGroup . GetAxisAlignedBoundingBox ( SelectedMeshGroupTransform . TotalTransform ) ;
Vector3 boundsCenter = selectedBounds . Center ;
Vector3 centerTop = new Vector3 ( boundsCenter . x , boundsCenter . y , selectedBounds . maxXYZ . z ) ;
2014-08-18 11:02:00 -07:00
2015-05-30 12:48:16 -07:00
Vector2 centerTopScreenPosition = meshViewerWidget . TrackballTumbleWidget . GetScreenPosition ( centerTop ) ;
centerTopScreenPosition = meshViewerWidget . TransformToParentSpace ( this , centerTopScreenPosition ) ;
//graphics2D.Circle(screenPosition.x, screenPosition.y, 5, RGBA_Bytes.Cyan);
PathStorage zArrow = new PathStorage ( ) ;
zArrow . MoveTo ( - 6 , - 2 ) ;
zArrow . curve3 ( 0 , - 4 ) ;
zArrow . LineTo ( 6 , - 2 ) ;
zArrow . LineTo ( 0 , 12 ) ;
zArrow . LineTo ( - 6 , - 2 ) ;
VertexSourceApplyTransform translate = new VertexSourceApplyTransform ( zArrow , Affine . NewTranslation ( centerTopScreenPosition ) ) ;
//graphics2D.Render(translate, RGBA_Bytes.Black);
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
}
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
private void ExitEditingAndSaveIfRequired ( bool response )
{
if ( response = = true )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
MergeAndSavePartsToCurrentMeshFile ( SwitchStateToNotEditing ) ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
else
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
SwitchStateToNotEditing ( ) ;
// and reload the part
ClearBedAndLoadPrintItemWrapper ( printItemWrapper ) ;
2015-04-08 15:20:10 -07:00
}
}
2014-01-29 19:09:30 -08:00
2015-05-30 12:48:16 -07:00
private void expandMaterialOptions_CheckedStateChanged ( object sender , EventArgs e )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( expandMaterialOptions . Checked = = true )
{
expandScaleOptions . Checked = false ;
expandRotateOptions . Checked = false ;
expandViewOptions . Checked = false ;
}
materialOptionContainer . Visible = expandMaterialOptions . Checked ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
private void expandMirrorOptions_CheckedStateChanged ( object sender , EventArgs e )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( mirrorOptionContainer . Visible ! = expandMirrorOptions . Checked )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( expandMirrorOptions . Checked = = true )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
expandScaleOptions . Checked = false ;
expandRotateOptions . Checked = false ;
expandViewOptions . Checked = false ;
expandMaterialOptions . Checked = false ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
mirrorOptionContainer . Visible = expandMirrorOptions . Checked ;
2015-04-08 15:20:10 -07:00
}
}
2015-05-30 12:48:16 -07:00
private void expandRotateOptions_CheckedStateChanged ( object sender , EventArgs e )
2015-01-23 21:56:44 -08:00
{
2015-05-30 12:48:16 -07:00
if ( rotateOptionContainer . Visible ! = expandRotateOptions . Checked )
2015-01-23 21:56:44 -08:00
{
2015-05-30 12:48:16 -07:00
if ( expandRotateOptions . Checked = = true )
{
expandViewOptions . Checked = false ;
expandScaleOptions . Checked = false ;
expandMirrorOptions . Checked = false ;
expandMaterialOptions . Checked = false ;
}
rotateOptionContainer . Visible = expandRotateOptions . Checked ;
2015-01-23 21:56:44 -08:00
}
}
2015-05-30 12:48:16 -07:00
private void expandScaleOptions_CheckedStateChanged ( object sender , EventArgs e )
2015-01-23 21:56:44 -08:00
{
2015-05-30 12:48:16 -07:00
if ( scaleOptionContainer . Visible ! = expandScaleOptions . Checked )
2015-01-23 21:56:44 -08:00
{
2015-05-30 12:48:16 -07:00
if ( expandScaleOptions . Checked = = true )
2015-01-23 21:56:44 -08:00
{
2015-05-30 12:48:16 -07:00
expandViewOptions . Checked = false ;
expandRotateOptions . Checked = false ;
expandMirrorOptions . Checked = false ;
expandMaterialOptions . Checked = false ;
2015-01-23 21:56:44 -08:00
}
2015-05-30 12:48:16 -07:00
scaleOptionContainer . Visible = expandScaleOptions . Checked ;
2015-01-23 21:56:44 -08:00
}
}
2014-05-16 17:13:18 -07:00
2015-05-30 12:48:16 -07:00
private void expandViewOptions_CheckedStateChanged ( object sender , EventArgs e )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( viewOptionContainer . Visible ! = expandViewOptions . Checked )
2015-01-23 21:56:44 -08:00
{
2015-05-30 12:48:16 -07:00
if ( expandViewOptions . Checked = = true )
2015-01-23 21:56:44 -08:00
{
2015-05-30 12:48:16 -07:00
expandScaleOptions . Checked = false ;
expandRotateOptions . Checked = false ;
expandMirrorOptions . Checked = false ;
expandMaterialOptions . Checked = false ;
2015-01-23 21:56:44 -08:00
}
2015-05-30 12:48:16 -07:00
viewOptionContainer . Visible = expandViewOptions . Checked ;
2015-01-23 21:56:44 -08:00
}
2015-04-08 15:20:10 -07:00
}
2014-05-16 17:13:18 -07:00
2015-05-30 12:48:16 -07:00
private bool FindMeshGroupHitPosition ( Vector2 screenPosition , out int meshHitIndex )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
meshHitIndex = 0 ;
if ( MeshGroupExtraData . Count = = 0 | | MeshGroupExtraData [ 0 ] . meshTraceableData = = null )
2015-01-23 21:56:44 -08:00
{
2015-05-30 12:48:16 -07:00
return false ;
}
List < IPrimitive > mesheTraceables = new List < IPrimitive > ( ) ;
for ( int i = 0 ; i < MeshGroupExtraData . Count ; i + + )
{
foreach ( IPrimitive traceData in MeshGroupExtraData [ i ] . meshTraceableData )
2015-01-23 21:56:44 -08:00
{
2015-05-30 12:48:16 -07:00
mesheTraceables . Add ( new Transform ( traceData , MeshGroupTransforms [ i ] . TotalTransform ) ) ;
2015-01-23 21:56:44 -08:00
}
2015-05-30 12:48:16 -07:00
}
IPrimitive allObjects = BoundingVolumeHierarchy . CreateNewHierachy ( mesheTraceables ) ;
2014-05-16 17:13:18 -07:00
2015-05-30 12:48:16 -07:00
Vector2 meshViewerWidgetScreenPosition = meshViewerWidget . TransformFromParentSpace ( this , screenPosition ) ;
Ray ray = meshViewerWidget . TrackballTumbleWidget . GetRayFromScreen ( meshViewerWidgetScreenPosition ) ;
IntersectInfo info = allObjects . GetClosestIntersection ( ray ) ;
if ( info ! = null )
{
meshSelectInfo . planeDownHitPos = info . hitPosition ;
meshSelectInfo . lastMoveDelta = new Vector3 ( ) ;
for ( int i = 0 ; i < MeshGroupExtraData . Count ; i + + )
2015-01-23 21:56:44 -08:00
{
2015-05-30 12:48:16 -07:00
List < IPrimitive > insideBounds = new List < IPrimitive > ( ) ;
foreach ( IPrimitive traceData in MeshGroupExtraData [ i ] . meshTraceableData )
2015-02-05 16:14:30 -08:00
{
2015-05-30 12:48:16 -07:00
traceData . GetContained ( insideBounds , info . closestHitObject . GetAxisAlignedBoundingBox ( ) ) ;
2015-02-05 16:14:30 -08:00
}
2015-05-30 12:48:16 -07:00
if ( insideBounds . Contains ( info . closestHitObject ) )
2015-02-05 16:14:30 -08:00
{
2015-05-30 12:48:16 -07:00
meshHitIndex = i ;
return true ;
2015-02-05 16:14:30 -08:00
}
2015-01-23 21:56:44 -08:00
}
}
2014-05-16 17:13:18 -07:00
2015-05-30 12:48:16 -07:00
return false ;
2015-04-08 15:20:10 -07:00
}
2014-05-16 17:13:18 -07:00
2015-05-30 12:48:16 -07:00
private GuiWidget generateHorizontalRule ( )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
GuiWidget horizontalRule = new GuiWidget ( ) ;
horizontalRule . Height = 1 ;
horizontalRule . Margin = new BorderDouble ( 0 , 1 , 0 , 3 ) ;
horizontalRule . HAnchor = HAnchor . ParentLeftRight ;
horizontalRule . BackgroundColor = new RGBA_Bytes ( 255 , 255 , 255 , 200 ) ;
return horizontalRule ;
}
2015-04-08 15:20:10 -07:00
2015-07-02 11:23:44 -07:00
private async void LoadAndAddPartsToPlate ( string [ ] filesToLoad )
2015-05-30 12:48:16 -07:00
{
if ( MeshGroups . Count > 0 & & filesToLoad ! = null & & filesToLoad . Length > 0 )
{
string loadingPartLabel = "Loading Parts" . Localize ( ) ;
string loadingPartLabelFull = "{0}:" . FormatWith ( loadingPartLabel ) ;
processingProgressControl . ProcessType = loadingPartLabelFull ;
processingProgressControl . Visible = true ;
processingProgressControl . PercentComplete = 0 ;
LockEditControls ( ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
PushMeshGroupDataToAsynchLists ( TraceInfoOpperation . DO_COPY ) ;
2015-04-08 15:20:10 -07:00
2015-07-02 11:23:44 -07:00
await Task . Run ( ( ) = > loadAndAddPartsToPlate ( filesToLoad ) ) ;
2015-04-08 15:20:10 -07:00
2015-07-02 11:23:44 -07:00
if ( WidgetHasBeenClosed )
{
return ;
}
UnlockEditControls ( ) ;
PartHasBeenChanged ( ) ;
bool addingOnlyOneItem = asynchMeshGroups . Count = = MeshGroups . Count + 1 ;
2015-04-08 15:20:10 -07:00
2015-07-02 11:23:44 -07:00
if ( MeshGroups . Count > 0 )
{
PullMeshGroupDataFromAsynchLists ( ) ;
if ( addingOnlyOneItem )
{
// if we are only adding one part to the plate set the selection to it
SelectedMeshGroupIndex = asynchMeshGroups . Count - 1 ;
}
}
2015-05-30 12:48:16 -07:00
}
2015-04-08 15:20:10 -07:00
}
2014-01-29 19:09:30 -08:00
2015-07-02 11:23:44 -07:00
private void loadAndAddPartsToPlate ( string [ ] filesToLoadIncludingZips )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
Thread . CurrentThread . CurrentCulture = CultureInfo . InvariantCulture ;
2014-05-16 12:57:49 -07:00
2015-05-30 12:48:16 -07:00
List < string > filesToLoad = new List < string > ( ) ;
if ( filesToLoadIncludingZips ! = null & & filesToLoadIncludingZips . Length > 0 )
{
for ( int i = 0 ; i < filesToLoadIncludingZips . Length ; i + + )
{
string loadedFileName = filesToLoadIncludingZips [ i ] ;
string extension = Path . GetExtension ( loadedFileName ) . ToUpper ( ) ;
2015-08-03 16:46:57 -07:00
if ( ( extension ! = "" & & MeshFileIo . ValidFileExtensions ( ) . Contains ( extension ) ) )
2015-05-30 12:48:16 -07:00
{
filesToLoad . Add ( loadedFileName ) ;
}
else if ( extension = = ".ZIP" )
{
ProjectFileHandler project = new ProjectFileHandler ( null ) ;
List < PrintItem > partFiles = project . ImportFromProjectArchive ( loadedFileName ) ;
if ( partFiles ! = null )
{
foreach ( PrintItem part in partFiles )
{
filesToLoad . Add ( part . FileLocation ) ;
}
}
}
}
2014-10-12 20:40:38 -07:00
2015-05-30 12:48:16 -07:00
string progressMessage = "Loading Parts..." . Localize ( ) ;
double ratioPerFile = 1.0 / filesToLoad . Count ;
double currentRatioDone = 0 ;
for ( int i = 0 ; i < filesToLoad . Count ; i + + )
{
string loadedFileName = filesToLoad [ i ] ;
List < MeshGroup > loadedMeshGroups = MeshFileIo . Load ( Path . GetFullPath ( loadedFileName ) , ( double progress0To1 , string processingState , out bool continueProcessing ) = >
{
continueProcessing = ! this . WidgetHasBeenClosed ;
double ratioAvailable = ( ratioPerFile * . 5 ) ;
double currentRatio = currentRatioDone + progress0To1 * ratioAvailable ;
2015-07-02 11:23:44 -07:00
ReportProgressChanged ( currentRatio , progressMessage , out continueProcessing ) ;
2015-05-30 12:48:16 -07:00
} ) ;
2014-01-29 19:09:30 -08:00
2015-05-30 12:48:16 -07:00
if ( WidgetHasBeenClosed )
{
return ;
}
if ( loadedMeshGroups ! = null )
{
double ratioPerSubMesh = ratioPerFile / loadedMeshGroups . Count ;
double subMeshRatioDone = 0 ;
2014-01-29 19:09:30 -08:00
2015-05-30 12:48:16 -07:00
for ( int subMeshIndex = 0 ; subMeshIndex < loadedMeshGroups . Count ; subMeshIndex + + )
{
MeshGroup meshGroup = loadedMeshGroups [ subMeshIndex ] ;
2014-01-29 19:09:30 -08:00
2015-05-30 12:48:16 -07:00
PlatingHelper . FindPositionForGroupAndAddToPlate ( meshGroup , ScaleRotateTranslate . Identity ( ) , asynchPlatingDatas , asynchMeshGroups , asynchMeshGroupTransforms ) ;
if ( WidgetHasBeenClosed )
{
return ;
}
PlatingHelper . CreateITraceableForMeshGroup ( asynchPlatingDatas , asynchMeshGroups , asynchMeshGroups . Count - 1 , ( double progress0To1 , string processingState , out bool continueProcessing ) = >
{
continueProcessing = ! this . WidgetHasBeenClosed ;
double ratioAvailable = ( ratioPerFile * . 5 ) ;
// done outer loop + done this loop +first 1/2 (load)+ this part * ratioAvailable
double currentRatio = currentRatioDone + subMeshRatioDone + ratioAvailable + progress0To1 * ratioPerSubMesh ;
2015-07-02 11:23:44 -07:00
ReportProgressChanged ( currentRatio , progressMessage , out continueProcessing ) ;
2015-05-30 12:48:16 -07:00
} ) ;
2014-01-29 19:09:30 -08:00
2015-05-30 12:48:16 -07:00
subMeshRatioDone + = ratioPerSubMesh ;
}
}
2014-01-29 19:09:30 -08:00
2015-05-30 12:48:16 -07:00
currentRatioDone + = ratioPerFile ;
}
}
}
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
private void LockEditControls ( )
{
viewIsInEditModePreLock = doEdittingButtonsContainer . Visible ;
enterEditButtonsContainer . Visible = false ;
doEdittingButtonsContainer . Visible = false ;
buttonRightPanelDisabledCover . Visible = true ;
if ( viewControls3D . PartSelectVisible = = true )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
viewControls3D . PartSelectVisible = false ;
2015-05-29 15:13:56 -07:00
if ( viewControls3D . ActiveButton = = ViewControls3DButtons . PartSelect )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
wasInSelectMode = true ;
2015-05-29 15:13:56 -07:00
viewControls3D . ActiveButton = ViewControls3DButtons . Rotate ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
}
2015-04-08 15:20:10 -07:00
}
2014-01-29 19:09:30 -08:00
2015-05-30 12:48:16 -07:00
private void MakeLowestFaceFlat ( int indexToLayFlat )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
Vertex lowestVertex = MeshGroups [ indexToLayFlat ] . Meshes [ 0 ] . Vertices [ 0 ] ;
Vector3 lowestVertexPosition = Vector3 . Transform ( lowestVertex . Position , MeshGroupTransforms [ indexToLayFlat ] . rotation ) ;
Mesh meshToLayFlat = null ;
foreach ( Mesh meshToCheck in MeshGroups [ indexToLayFlat ] . Meshes )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
// find the lowest point on the model
for ( int testIndex = 1 ; testIndex < meshToCheck . Vertices . Count ; testIndex + + )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
Vertex vertex = meshToCheck . Vertices [ testIndex ] ;
Vector3 vertexPosition = Vector3 . Transform ( vertex . Position , MeshGroupTransforms [ indexToLayFlat ] . rotation ) ;
if ( vertexPosition . z < lowestVertexPosition . z )
{
lowestVertex = meshToCheck . Vertices [ testIndex ] ;
lowestVertexPosition = vertexPosition ;
meshToLayFlat = meshToCheck ;
}
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
}
2014-01-29 19:09:30 -08:00
2015-05-30 12:48:16 -07:00
Face faceToLayFlat = null ;
double lowestAngleOfAnyFace = double . MaxValue ;
// Check all the faces that are connected to the lowest point to find out which one to lay flat.
foreach ( Face face in lowestVertex . ConnectedFaces ( ) )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
double biggestAngleToFaceVertex = double . MinValue ;
foreach ( Vertex faceVertex in face . Vertices ( ) )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( faceVertex ! = lowestVertex )
{
Vector3 faceVertexPosition = Vector3 . Transform ( faceVertex . Position , MeshGroupTransforms [ indexToLayFlat ] . rotation ) ;
Vector3 pointRelLowest = faceVertexPosition - lowestVertexPosition ;
double xLeg = new Vector2 ( pointRelLowest . x , pointRelLowest . y ) . Length ;
double yLeg = pointRelLowest . z ;
double angle = Math . Atan2 ( yLeg , xLeg ) ;
if ( angle > biggestAngleToFaceVertex )
{
biggestAngleToFaceVertex = angle ;
}
}
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
if ( biggestAngleToFaceVertex < lowestAngleOfAnyFace )
{
lowestAngleOfAnyFace = biggestAngleToFaceVertex ;
faceToLayFlat = face ;
}
}
2014-01-29 19:09:30 -08:00
2015-05-30 12:48:16 -07:00
double maxDistFromLowestZ = 0 ;
List < Vector3 > faceVertexes = new List < Vector3 > ( ) ;
foreach ( Vertex vertex in faceToLayFlat . Vertices ( ) )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
Vector3 vertexPosition = Vector3 . Transform ( vertex . Position , MeshGroupTransforms [ indexToLayFlat ] . rotation ) ;
faceVertexes . Add ( vertexPosition ) ;
maxDistFromLowestZ = Math . Max ( maxDistFromLowestZ , vertexPosition . z - lowestVertexPosition . z ) ;
}
2014-10-12 08:18:24 -07:00
2015-05-30 12:48:16 -07:00
if ( maxDistFromLowestZ > . 001 )
{
Vector3 xPositive = ( faceVertexes [ 1 ] - faceVertexes [ 0 ] ) . GetNormal ( ) ;
Vector3 yPositive = ( faceVertexes [ 2 ] - faceVertexes [ 0 ] ) . GetNormal ( ) ;
Vector3 planeNormal = Vector3 . Cross ( xPositive , yPositive ) . GetNormal ( ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
// this code takes the minimum rotation required and looks much better.
Quaternion rotation = new Quaternion ( planeNormal , new Vector3 ( 0 , 0 , - 1 ) ) ;
Matrix4X4 partLevelMatrix = Matrix4X4 . CreateRotation ( rotation ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
// rotate it
ScaleRotateTranslate rotated = SelectedMeshGroupTransform ;
rotated . rotation * = partLevelMatrix ;
SelectedMeshGroupTransform = rotated ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
PlatingHelper . PlaceMeshGroupOnBed ( MeshGroups , MeshGroupTransforms , SelectedMeshGroupIndex ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
PartHasBeenChanged ( ) ;
Invalidate ( ) ;
}
}
2015-09-09 11:05:17 -07:00
private void MergeAndSavePartsDoWork ( SaveAsWindow . SaveAsReturnInfo returnInfo )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( returnInfo ! = null )
2015-04-08 15:20:10 -07:00
{
2015-08-31 16:32:09 -07:00
PrintItem printItem = new PrintItem ( ) ;
printItem . Name = returnInfo . newName ;
printItem . FileLocation = Path . GetFullPath ( returnInfo . fileNameAndPath ) ;
2015-09-11 14:36:57 -07:00
printItemWrapper = new PrintItemWrapper ( printItem , returnInfo . destinationLibraryProvider . GetProviderLocator ( ) ) ;
2015-05-30 12:48:16 -07:00
}
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
// we sent the data to the asynch lists but we will not pull it back out (only use it as a temp holder).
PushMeshGroupDataToAsynchLists ( TraceInfoOpperation . DO_COPY ) ;
Thread . CurrentThread . CurrentCulture = CultureInfo . InvariantCulture ;
try
{
// push all the transforms into the meshes
for ( int i = 0 ; i < asynchMeshGroups . Count ; i + + )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
asynchMeshGroups [ i ] . Transform ( asynchMeshGroupTransforms [ i ] . TotalTransform ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
bool continueProcessing ;
2015-07-02 11:23:44 -07:00
ReportProgressChanged ( ( i + 1 ) * . 4 / asynchMeshGroups . Count , "" , out continueProcessing ) ;
2015-05-30 12:48:16 -07:00
}
2015-07-17 16:12:14 -07:00
string [ ] metaData = { "Created By" , "MatterControl" , "BedPosition" , "Absolute" } ;
MeshOutputSettings outputInfo = new MeshOutputSettings ( MeshOutputSettings . OutputType . Binary , metaData ) ;
2015-09-09 11:05:17 -07:00
if ( Path . GetExtension ( printItemWrapper . FileLocation ) . ToUpper ( ) = = ".STL" )
{
printItemWrapper . FileLocation = Path . ChangeExtension ( printItemWrapper . FileLocation , ".AMF" ) ;
}
2015-11-04 17:42:07 -08:00
MeshFileIo . Save ( asynchMeshGroups , printItemWrapper . FileLocation , outputInfo , ReportProgressChanged ) ;
2015-08-31 16:32:09 -07:00
2015-11-04 12:20:20 -08:00
// Wait for a second to report the file changed to give the OS a chance to finish closing it.
UiThread . RunOnIdle ( printItemWrapper . ReportFileChange , 3 ) ;
2015-09-23 13:33:14 -07:00
2015-08-31 16:32:09 -07:00
if ( returnInfo ! = null
& & returnInfo . destinationLibraryProvider ! = null )
{
// save this part to correct library provider
2015-09-11 14:36:57 -07:00
LibraryProvider libraryToSaveTo = returnInfo . destinationLibraryProvider ;
if ( libraryToSaveTo ! = null )
{
libraryToSaveTo . AddItem ( printItemWrapper ) ;
libraryToSaveTo . Dispose ( ) ;
}
2015-08-31 16:32:09 -07:00
}
else // we have already save it and the library should pick it up
{
}
2015-11-04 17:42:07 -08:00
saveSucceded = true ;
2015-05-30 12:48:16 -07:00
}
2015-09-11 10:48:24 -07:00
catch ( System . UnauthorizedAccessException e2 )
2015-05-30 12:48:16 -07:00
{
2015-09-11 10:48:24 -07:00
Debug . Print ( e2 . Message ) ;
2015-09-17 13:45:26 -07:00
GuiWidget . BreakInDebugger ( ) ;
2015-05-30 12:48:16 -07:00
saveSucceded = false ;
2015-06-11 12:06:40 -07:00
UiThread . RunOnIdle ( ( ) = >
2015-05-30 12:48:16 -07:00
{
//Do something special when unauthorized?
StyledMessageBox . ShowMessageBox ( null , "Oops! Unable to save changes." , "Unable to save" ) ;
} ) ;
}
2015-12-22 15:26:51 -08:00
catch ( Exception e )
2015-05-30 12:48:16 -07:00
{
2015-09-11 10:48:24 -07:00
Debug . Print ( e . Message ) ;
2015-09-17 13:45:26 -07:00
GuiWidget . BreakInDebugger ( ) ;
2015-05-30 12:48:16 -07:00
saveSucceded = false ;
2015-06-11 12:06:40 -07:00
UiThread . RunOnIdle ( ( ) = >
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
StyledMessageBox . ShowMessageBox ( null , "Oops! Unable to save changes." , "Unable to save" ) ;
} ) ;
}
}
2014-10-13 18:20:01 -07:00
2015-09-09 11:05:17 -07:00
private void MergeAndSavePartsDoCompleted ( )
2015-05-30 12:48:16 -07:00
{
if ( WidgetHasBeenClosed )
{
return ;
}
UnlockEditControls ( ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
// NOTE: we do not pull the data back out of the asynch lists.
if ( saveSucceded )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
saveButtons . Visible = false ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
if ( afterSaveCallback ! = null )
{
afterSaveCallback ( ) ;
}
2015-04-08 15:20:10 -07:00
}
2015-09-09 11:05:17 -07:00
private async void MergeAndSavePartsToCurrentMeshFile ( Action eventToCallAfterSave = null )
2015-04-08 15:20:10 -07:00
{
2015-04-15 16:59:12 -07:00
editorThatRequestedSave = true ;
2015-05-30 12:48:16 -07:00
afterSaveCallback = eventToCallAfterSave ;
2015-04-08 15:20:10 -07:00
if ( MeshGroups . Count > 0 )
{
string progressSavingPartsLabel = "Saving" . Localize ( ) ;
string progressSavingPartsLabelFull = "{0}:" . FormatWith ( progressSavingPartsLabel ) ;
processingProgressControl . ProcessType = progressSavingPartsLabelFull ;
processingProgressControl . Visible = true ;
processingProgressControl . PercentComplete = 0 ;
LockEditControls ( ) ;
2015-09-09 11:05:17 -07:00
await Task . Run ( ( ) = > MergeAndSavePartsDoWork ( null ) ) ;
MergeAndSavePartsDoCompleted ( ) ;
2015-04-08 15:20:10 -07:00
}
}
2014-01-29 19:09:30 -08:00
2015-09-09 11:05:17 -07:00
private async void MergeAndSavePartsToNewMeshFile ( SaveAsWindow . SaveAsReturnInfo returnInfo )
2015-04-08 15:20:10 -07:00
{
2015-04-16 10:38:53 -07:00
editorThatRequestedSave = true ;
2015-04-08 15:20:10 -07:00
if ( MeshGroups . Count > 0 )
{
string progressSavingPartsLabel = "Saving" . Localize ( ) ;
string progressSavingPartsLabelFull = "{0}:" . FormatWith ( progressSavingPartsLabel ) ;
processingProgressControl . ProcessType = progressSavingPartsLabelFull ;
processingProgressControl . Visible = true ;
processingProgressControl . PercentComplete = 0 ;
LockEditControls ( ) ;
2015-09-09 11:05:17 -07:00
await Task . Run ( ( ) = > MergeAndSavePartsDoWork ( returnInfo ) ) ;
MergeAndSavePartsDoCompleted ( ) ;
2015-04-08 15:20:10 -07:00
}
}
2015-05-30 12:48:16 -07:00
private void meshViewerWidget_LoadDone ( object sender , EventArgs e )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( windowType = = WindowMode . Embeded )
{
switch ( PrinterConnectionAndCommunication . Instance . CommunicationState )
{
case PrinterConnectionAndCommunication . CommunicationStates . Printing :
case PrinterConnectionAndCommunication . CommunicationStates . Paused :
break ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
default :
UnlockEditControls ( ) ;
break ;
}
}
else
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
UnlockEditControls ( ) ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
SelectionChanged ( this , null ) ;
2015-04-08 15:20:10 -07:00
2015-08-29 09:23:04 -07:00
if ( openMode = = OpenMode . Editing )
2015-04-08 15:20:10 -07:00
{
2015-06-11 12:06:40 -07:00
UiThread . RunOnIdle ( EnterEditAndCreateSelectionData ) ;
2015-05-30 12:48:16 -07:00
}
2015-11-09 12:36:47 -08:00
SetDefaultView ( ) ;
2015-05-30 12:48:16 -07:00
}
2015-04-08 15:20:10 -07:00
2015-08-06 15:20:04 -07:00
private bool PartsAreInPrintVolume ( )
{
2015-12-22 15:26:51 -08:00
if ( ActiveSliceSettings . Instance ! = null
& & ! ActiveSliceSettings . Instance . CenterOnBed ( )
2015-08-10 15:35:56 -07:00
& & ActivePrinterProfile . Instance . ActivePrinter ! = null )
{
AxisAlignedBoundingBox allBounds = MeshViewerWidget . GetAxisAlignedBoundingBox ( MeshGroups ) ;
bool onBed = allBounds . minXYZ . z > - . 001 & & allBounds . minXYZ . z < . 001 ; // really close to the bed
RectangleDouble bedRect = new RectangleDouble ( 0 , 0 , ActiveSliceSettings . Instance . BedSize . x , ActiveSliceSettings . Instance . BedSize . y ) ;
bedRect . Offset ( ActiveSliceSettings . Instance . BedCenter - ActiveSliceSettings . Instance . BedSize / 2 ) ;
bool inBounds = bedRect . Contains ( new Vector2 ( allBounds . minXYZ ) ) & & bedRect . Contains ( new Vector2 ( allBounds . maxXYZ ) ) ;
2015-08-06 15:20:04 -07:00
2015-08-10 15:35:56 -07:00
return onBed & & inBounds ;
}
2015-08-06 15:20:04 -07:00
2015-08-10 15:35:56 -07:00
return true ;
2015-08-06 15:20:04 -07:00
}
2015-05-30 12:48:16 -07:00
private void OpenExportWindow ( )
{
if ( exportingWindow = = null )
{
exportingWindow = new ExportPrintItemWindow ( this . printItemWrapper ) ;
exportingWindow . Closed + = ( sender , e ) = >
{
exportingWindow = null ;
} ;
exportingWindow . ShowAsSystemWindow ( ) ;
}
else
{
exportingWindow . BringToFront ( ) ;
}
}
2014-01-29 19:09:30 -08:00
2015-06-11 12:06:40 -07:00
private void OpenSaveAsWindow ( )
2015-05-30 12:48:16 -07:00
{
if ( saveAsWindow = = null )
{
2015-07-31 18:18:21 -07:00
List < ProviderLocatorNode > providerLocator = null ;
2015-09-11 14:36:57 -07:00
if ( printItemWrapper . SourceLibraryProviderLocator ! = null )
2015-07-31 18:18:21 -07:00
{
2015-09-11 14:36:57 -07:00
providerLocator = printItemWrapper . SourceLibraryProviderLocator ;
2015-07-31 18:18:21 -07:00
}
2015-09-04 13:47:48 -07:00
saveAsWindow = new SaveAsWindow ( MergeAndSavePartsToNewMeshFile , providerLocator , true , true ) ;
2015-05-30 12:48:16 -07:00
saveAsWindow . Closed + = new EventHandler ( SaveAsWindow_Closed ) ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
else
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
saveAsWindow . BringToFront ( ) ;
}
}
private void PullMeshGroupDataFromAsynchLists ( )
{
if ( MeshGroups . Count ! = asynchMeshGroups . Count )
{
PartHasBeenChanged ( ) ;
}
MeshGroups . Clear ( ) ;
foreach ( MeshGroup meshGroup in asynchMeshGroups )
{
MeshGroups . Add ( meshGroup ) ;
}
MeshGroupTransforms . Clear ( ) ;
foreach ( ScaleRotateTranslate transform in asynchMeshGroupTransforms )
{
MeshGroupTransforms . Add ( transform ) ;
}
MeshGroupExtraData . Clear ( ) ;
foreach ( PlatingMeshGroupData meshData in asynchPlatingDatas )
{
MeshGroupExtraData . Add ( meshData ) ;
}
if ( MeshGroups . Count ! = MeshGroupTransforms . Count
| | MeshGroups . Count ! = MeshGroupExtraData . Count )
{
throw new Exception ( "These all need to remain in sync." ) ;
}
}
private void PushMeshGroupDataToAsynchLists ( TraceInfoOpperation traceInfoOpperation , ReportProgressRatio reportProgress = null )
{
2015-06-11 12:06:40 -07:00
UiThread . RunOnIdle ( ( ) = >
2015-05-30 12:48:16 -07:00
{
processingProgressControl . ProgressMessage = "Async Copy" ;
} ) ;
asynchMeshGroups . Clear ( ) ;
asynchMeshGroupTransforms . Clear ( ) ;
for ( int meshGroupIndex = 0 ; meshGroupIndex < MeshGroups . Count ; meshGroupIndex + + )
{
MeshGroup meshGroup = MeshGroups [ meshGroupIndex ] ;
MeshGroup newMeshGroup = new MeshGroup ( ) ;
for ( int meshIndex = 0 ; meshIndex < meshGroup . Meshes . Count ; meshIndex + + )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
Mesh mesh = meshGroup . Meshes [ meshIndex ] ;
newMeshGroup . Meshes . Add ( Mesh . Copy ( mesh ) ) ;
}
asynchMeshGroups . Add ( newMeshGroup ) ;
asynchMeshGroupTransforms . Add ( MeshGroupTransforms [ meshGroupIndex ] ) ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
asynchPlatingDatas . Clear ( ) ;
for ( int meshGroupIndex = 0 ; meshGroupIndex < MeshGroupExtraData . Count ; meshGroupIndex + + )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
PlatingMeshGroupData meshData = new PlatingMeshGroupData ( ) ;
meshData . currentScale = MeshGroupExtraData [ meshGroupIndex ] . currentScale ;
MeshGroup meshGroup = MeshGroups [ meshGroupIndex ] ;
if ( traceInfoOpperation = = TraceInfoOpperation . DO_COPY )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
meshData . meshTraceableData . AddRange ( MeshGroupExtraData [ meshGroupIndex ] . meshTraceableData ) ;
}
asynchPlatingDatas . Add ( meshData ) ;
}
2015-06-11 12:06:40 -07:00
UiThread . RunOnIdle ( ( ) = >
2015-05-30 12:48:16 -07:00
{
processingProgressControl . ProgressMessage = "" ;
} ) ;
}
private void ReloadMeshIfChangeExternaly ( Object sender , EventArgs e )
{
2015-09-23 13:33:14 -07:00
PrintItemWrapper senderItem = sender as PrintItemWrapper ;
if ( senderItem ! = null
& & senderItem . FileLocation = = printItemWrapper . FileLocation )
2015-05-30 12:48:16 -07:00
{
2015-09-23 13:33:14 -07:00
if ( ! editorThatRequestedSave )
{
ClearBedAndLoadPrintItemWrapper ( printItemWrapper ) ;
}
2014-11-11 12:09:09 -08:00
2015-09-23 13:33:14 -07:00
editorThatRequestedSave = false ;
}
2015-05-30 12:48:16 -07:00
}
private bool rotateQueueMenu_Click ( )
{
return true ;
}
private void SaveAsWindow_Closed ( object sender , EventArgs e )
{
this . saveAsWindow = null ;
}
private void ScaleAxis ( double scaleIn , int axis )
{
AxisAlignedBoundingBox originalMeshBounds = SelectedMeshGroup . GetAxisAlignedBoundingBox ( ) ;
2015-10-16 12:36:09 -07:00
AxisAlignedBoundingBox totalMeshBounds = SelectedMeshGroup . GetAxisAlignedBoundingBox ( SelectedMeshGroupTransform . TotalTransform ) ;
2015-05-30 12:48:16 -07:00
AxisAlignedBoundingBox scaledBounds = SelectedMeshGroup . GetAxisAlignedBoundingBox ( SelectedMeshGroupTransform . scale ) ;
// first we remove any scale we have applied and then scale to the new value
Vector3 axisRemoveScalings = new Vector3 ( ) ;
axisRemoveScalings . x = scaledBounds . Size . x / originalMeshBounds . Size . x ;
axisRemoveScalings . y = scaledBounds . Size . y / originalMeshBounds . Size . y ;
axisRemoveScalings . z = scaledBounds . Size . z / originalMeshBounds . Size . z ;
Matrix4X4 removeScaleMatrix = Matrix4X4 . CreateScale ( 1 / axisRemoveScalings ) ;
Vector3 newScale = MeshGroupExtraData [ SelectedMeshGroupIndex ] . currentScale ;
newScale [ axis ] = scaleIn ;
Matrix4X4 totalScale = removeScaleMatrix * Matrix4X4 . CreateScale ( newScale ) ;
ScaleRotateTranslate scale = SelectedMeshGroupTransform ;
scale . scale * = totalScale ;
SelectedMeshGroupTransform = scale ;
2015-10-16 12:36:09 -07:00
// And make sure its center has not changed
AxisAlignedBoundingBox postScaleBounds = SelectedMeshGroup . GetAxisAlignedBoundingBox ( SelectedMeshGroupTransform . TotalTransform ) ;
ScaleRotateTranslate translation = SelectedMeshGroupTransform ;
translation . translation * = Matrix4X4 . CreateTranslation ( totalMeshBounds . Center - postScaleBounds . Center ) ;
SelectedMeshGroupTransform = translation ;
2015-05-30 12:48:16 -07:00
PlatingHelper . PlaceMeshGroupOnBed ( MeshGroups , MeshGroupTransforms , SelectedMeshGroupIndex ) ;
2015-10-16 12:36:09 -07:00
2015-05-30 12:48:16 -07:00
PartHasBeenChanged ( ) ;
Invalidate ( ) ;
MeshGroupExtraData [ SelectedMeshGroupIndex ] . currentScale [ axis ] = scaleIn ;
SetApplyScaleVisability ( this , null ) ;
2015-04-08 15:20:10 -07:00
}
2014-01-29 19:09:30 -08:00
2015-05-30 12:48:16 -07:00
private bool scaleQueueMenu_Click ( )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
return true ;
}
2014-11-11 12:09:09 -08:00
2015-05-30 12:48:16 -07:00
private void SetApplyScaleVisability ( Object sender , EventArgs e )
{
if ( HaveSelection )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
double scale = scaleRatioControl . ActuallNumberEdit . Value ;
if ( scale ! = MeshGroupExtraData [ SelectedMeshGroupIndex ] . currentScale [ 0 ]
| | scale ! = MeshGroupExtraData [ SelectedMeshGroupIndex ] . currentScale [ 1 ]
| | scale ! = MeshGroupExtraData [ SelectedMeshGroupIndex ] . currentScale [ 2 ] )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
applyScaleButton . Visible = true ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
else
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
applyScaleButton . Visible = false ;
2015-04-08 15:20:10 -07:00
}
}
2014-11-11 12:09:09 -08:00
2015-05-30 12:48:16 -07:00
UpdateSizeInfo ( ) ;
2015-04-08 15:20:10 -07:00
}
2014-01-29 19:09:30 -08:00
2015-05-30 12:48:16 -07:00
private void SetEditControlsBasedOnPrinterState ( object sender , EventArgs e )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( windowType = = WindowMode . Embeded )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
switch ( PrinterConnectionAndCommunication . Instance . CommunicationState )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
case PrinterConnectionAndCommunication . CommunicationStates . Printing :
case PrinterConnectionAndCommunication . CommunicationStates . Paused :
LockEditControls ( ) ;
break ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
default :
UnlockEditControls ( ) ;
break ;
2015-04-08 15:20:10 -07:00
}
}
}
2015-05-30 12:48:16 -07:00
private void SetNewModelSize ( double sizeInMm , int axis )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( HaveSelection )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
// because we remove any current scale before we change to a new one we only get the size of the base mesh data
AxisAlignedBoundingBox originalMeshBounds = SelectedMeshGroup . GetAxisAlignedBoundingBox ( ) ;
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
double currentSize = originalMeshBounds . Size [ axis ] ;
double desiredSize = sizeDisplay [ axis ] . GetValue ( ) ;
double scaleFactor = 1 ;
if ( currentSize ! = 0 )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
scaleFactor = desiredSize / currentSize ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
if ( uniformScale . Checked )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
scaleRatioControl . ActuallNumberEdit . Value = scaleFactor ;
ApplyScaleFromEditField ( ) ;
}
else
{
ScaleAxis ( scaleFactor , axis ) ;
2015-04-08 15:20:10 -07:00
}
}
}
2015-05-30 12:48:16 -07:00
private void SwitchStateToNotEditing ( )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( ! enterEditButtonsContainer . Visible )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
enterEditButtonsContainer . Visible = true ;
processingProgressControl . Visible = false ;
buttonRightPanel . Visible = false ;
doEdittingButtonsContainer . Visible = false ;
viewControls3D . PartSelectVisible = false ;
2015-05-29 15:13:56 -07:00
if ( viewControls3D . ActiveButton = = ViewControls3DButtons . PartSelect )
2015-04-08 15:20:10 -07:00
{
2015-05-29 15:13:56 -07:00
viewControls3D . ActiveButton = ViewControls3DButtons . Rotate ;
2015-12-22 15:26:51 -08:00
}
2015-05-30 12:48:16 -07:00
SelectedMeshGroupIndex = - 1 ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
}
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
private void UnlockEditControls ( )
{
buttonRightPanelDisabledCover . Visible = false ;
processingProgressControl . Visible = false ;
if ( viewIsInEditModePreLock )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
if ( ! enterEditButtonsContainer . Visible )
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
viewControls3D . PartSelectVisible = true ;
doEdittingButtonsContainer . Visible = true ;
2015-04-08 15:20:10 -07:00
}
}
2015-05-30 12:48:16 -07:00
else
2015-04-08 15:20:10 -07:00
{
2015-05-30 12:48:16 -07:00
enterEditButtonsContainer . Visible = true ;
2015-04-08 15:20:10 -07:00
}
2015-05-30 12:48:16 -07:00
if ( wasInSelectMode )
2015-04-08 15:20:10 -07:00
{
2015-05-29 15:13:56 -07:00
viewControls3D . ActiveButton = ViewControls3DButtons . PartSelect ;
2015-05-30 12:48:16 -07:00
wasInSelectMode = false ;
}
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
UpdateSizeInfo ( ) ;
}
2015-04-08 15:20:10 -07:00
2015-05-30 12:48:16 -07:00
private void UpdateSizeInfo ( )
{
if ( sizeDisplay [ 0 ] ! = null
& & SelectedMeshGroup ! = null )
{
AxisAlignedBoundingBox bounds = SelectedMeshGroup . GetAxisAlignedBoundingBox ( SelectedMeshGroupTransform . scale ) ;
sizeDisplay [ 0 ] . SetDisplayString ( "{0:0.00}" . FormatWith ( bounds . Size [ 0 ] ) ) ;
sizeDisplay [ 1 ] . SetDisplayString ( "{0:0.00}" . FormatWith ( bounds . Size [ 1 ] ) ) ;
sizeDisplay [ 2 ] . SetDisplayString ( "{0:0.00}" . FormatWith ( bounds . Size [ 2 ] ) ) ;
}
else
{
sizeDisplay [ 0 ] . SetDisplayString ( "---" ) ;
sizeDisplay [ 1 ] . SetDisplayString ( "---" ) ;
sizeDisplay [ 2 ] . SetDisplayString ( "---" ) ;
2015-04-08 15:20:10 -07:00
}
}
2015-05-30 12:48:16 -07:00
internal struct MeshSelectInfo
{
internal bool downOnPart ;
internal PlaneShape hitPlane ;
internal Vector3 lastMoveDelta ;
internal Vector3 planeDownHitPos ;
}
2015-04-08 15:20:10 -07:00
}
}