2019-12-27 09:26:59 -05:00
// Copyright Epic Games, Inc. All Rights Reserved.
2019-10-01 20:41:42 -04:00
# include "AddPrimitiveTool.h"
# include "ToolBuilderUtil.h"
# include "InteractiveToolManager.h"
2021-10-21 16:57:00 -04:00
# include "SceneQueries/SceneSnappingManager.h"
2019-10-01 20:41:42 -04:00
# include "BaseBehaviors/MouseHoverBehavior.h"
# include "Selection/ToolSelectionUtil.h"
2021-06-02 15:58:00 -04:00
# include "ModelingObjectsCreationAPI.h"
2020-10-22 19:19:16 -04:00
# include "ToolSceneQueriesUtil.h"
2021-10-07 22:25:54 -04:00
# include "ToolSetupUtil.h"
2019-10-01 20:41:42 -04:00
2019-10-25 20:21:29 -04:00
# include "Components/StaticMeshComponent.h"
# include "Engine/StaticMeshActor.h"
2019-10-01 20:41:42 -04:00
# include "Generators/SweepGenerator.h"
# include "Generators/GridBoxMeshGenerator.h"
# include "Generators/RectangleMeshGenerator.h"
# include "Generators/SphereGenerator.h"
2019-10-21 20:08:02 -04:00
# include "Generators/BoxSphereGenerator.h"
2019-10-24 03:25:01 -04:00
# include "Generators/DiscMeshGenerator.h"
2021-02-17 10:26:34 -04:00
# include "Generators/StairGenerator.h"
2021-06-13 00:36:02 -04:00
# include "DynamicMesh/DynamicMeshAttributeSet.h"
2020-03-10 16:54:55 -04:00
# include "FaceGroupUtil.h"
2020-01-27 20:11:15 -05:00
2019-10-01 20:41:42 -04:00
# include "DynamicMeshEditor.h"
2020-04-18 18:42:59 -04:00
# include "UObject/PropertyIterator.h"
# include "UObject/UnrealType.h"
2019-10-01 20:41:42 -04:00
2021-03-09 19:33:56 -04:00
using namespace UE : : Geometry ;
2019-10-01 20:41:42 -04:00
2021-03-09 19:33:56 -04:00
# define LOCTEXT_NAMESPACE "UAddPrimitiveTool"
2019-10-01 20:41:42 -04:00
/*
* ToolBuilder
*/
bool UAddPrimitiveToolBuilder : : CanBuildTool ( const FToolBuilderState & SceneState ) const
{
2021-06-02 15:58:00 -04:00
return true ;
2019-10-01 20:41:42 -04:00
}
UInteractiveTool * UAddPrimitiveToolBuilder : : BuildTool ( const FToolBuilderState & SceneState ) const
{
2020-04-18 18:42:59 -04:00
UAddPrimitiveTool * NewTool = nullptr ;
switch ( ShapeType )
{
case EMakeMeshShapeType : : Box :
NewTool = NewObject < UAddBoxPrimitiveTool > ( SceneState . ToolManager ) ;
break ;
case EMakeMeshShapeType : : Cylinder :
NewTool = NewObject < UAddCylinderPrimitiveTool > ( SceneState . ToolManager ) ;
break ;
case EMakeMeshShapeType : : Cone :
NewTool = NewObject < UAddConePrimitiveTool > ( SceneState . ToolManager ) ;
break ;
case EMakeMeshShapeType : : Arrow :
NewTool = NewObject < UAddArrowPrimitiveTool > ( SceneState . ToolManager ) ;
break ;
case EMakeMeshShapeType : : Rectangle :
NewTool = NewObject < UAddRectanglePrimitiveTool > ( SceneState . ToolManager ) ;
break ;
case EMakeMeshShapeType : : Disc :
NewTool = NewObject < UAddDiscPrimitiveTool > ( SceneState . ToolManager ) ;
break ;
case EMakeMeshShapeType : : Torus :
NewTool = NewObject < UAddTorusPrimitiveTool > ( SceneState . ToolManager ) ;
break ;
case EMakeMeshShapeType : : Sphere :
NewTool = NewObject < UAddSpherePrimitiveTool > ( SceneState . ToolManager ) ;
break ;
2021-02-25 13:48:43 -04:00
case EMakeMeshShapeType : : Stairs :
NewTool = NewObject < UAddStairsPrimitiveTool > ( SceneState . ToolManager ) ;
2021-02-17 10:26:34 -04:00
break ;
2020-04-18 18:42:59 -04:00
default :
break ;
}
2019-10-01 20:41:42 -04:00
NewTool - > SetWorld ( SceneState . World ) ;
return NewTool ;
}
bool
2020-04-18 18:42:59 -04:00
UProceduralShapeToolProperties : : IsEquivalent ( const UProceduralShapeToolProperties * Other ) const
2019-10-01 20:41:42 -04:00
{
2020-04-18 18:42:59 -04:00
# if WITH_EDITOR
UClass * Class = GetClass ( ) ;
if ( Other - > GetClass ( ) ! = Class )
2019-10-01 20:41:42 -04:00
{
2020-04-18 18:42:59 -04:00
return false ;
2019-10-01 20:41:42 -04:00
}
2021-10-18 14:21:53 -04:00
for ( const FProperty * Prop : TFieldRange < FProperty > ( Class ) )
2020-04-18 18:42:59 -04:00
{
if ( Prop - > HasMetaData ( TEXT ( " ProceduralShapeSetting " ) ) & &
( ! Prop - > Identical_InContainer ( this , Other ) ) )
{
return false ;
}
}
return true ;
# else
2019-10-01 20:41:42 -04:00
return false ;
2020-04-18 18:42:59 -04:00
# endif
2019-10-01 20:41:42 -04:00
}
void UAddPrimitiveTool : : SetWorld ( UWorld * World )
{
this - > TargetWorld = World ;
}
2020-04-18 18:42:59 -04:00
UAddPrimitiveTool : : UAddPrimitiveTool ( const FObjectInitializer & )
{
ShapeSettings = CreateDefaultSubobject < UProceduralShapeToolProperties > ( TEXT ( " ShapeSettings " ) ) ;
2021-03-24 18:11:10 -04:00
// CreateDefaultSubobject automatically sets RF_Transactional flag, we need to clear it so that undo/redo doesn't affect tool properties
ShapeSettings - > ClearFlags ( RF_Transactional ) ;
2020-04-18 18:42:59 -04:00
}
2019-10-01 20:41:42 -04:00
void UAddPrimitiveTool : : Setup ( )
{
USingleClickTool : : Setup ( ) ;
UMouseHoverBehavior * HoverBehavior = NewObject < UMouseHoverBehavior > ( this ) ;
HoverBehavior - > Initialize ( this ) ;
AddInputBehavior ( HoverBehavior ) ;
ModelingTools: add support for creating Volumes directly from DrawPolygon, DrawRevolve, DrawPolyPath, and AddPrimitive, CombineMeshes, CutMeshWithMesh, PlaneCut, BaseCreateFromSelected Tools. Improve support for Editing volumes, eg handling mesh/volume interactions, and add configurable auto-simplification for volumes to avoid painful Editor hangs.
- Move ToolTarget implementations, DynamicMeshToVolume to ModelingComponentsEditorOnly module
- move VolumeToDynamicMesh, DynamicMeshProvider/Commiter interfaces to ModelingComponents module
- Add UCreateMeshObjectTypeProperties property set to expose mesh/volume options
- Add FCreateMeshObjectParams::TypeHintClass to allow AVolume type (or other UClass hints) to be passed to creation APIs
- Add UE::ToolTarget::ConfigureCreateMeshObjectParams() util function in ModelingToolTargetUtil, tries to determine output type in a FCreateMeshObjectParams based on input ToolTarget
- Add UEditorModelingObjectsCreationAPI::CreateVolume() implementation
- Add UEditorModelingObjectsCreationAPI::FilterMaterials() that strips out any internal materials and replaces with WorldGridMaterial. This occurs when (eg) subtracting a Volume from a StaticMesh, because the temporary volume mesh gets assigned internal materials, but the Tools don't know this. Use in EditorModelingObjectsCreationAPI when creating new objects. UStaticMeshComponentToolTarget also does this filtering in ::CommitMaterialSetUpdate().
- Add ::ComponentTypeSupportsCollision() function to ComponentCollisionUtil, use to avoid checks/ensures for Volume targets
- Add support for automatic mesh simplification in DynamicMeshToVolume. Add CVar to VolumeDynamicMeshToolTarget.h to control max triangle count (default 500). Apply auto-simplify when creating or updating an AVolume. This prevents the Editor from blocking for long periods on meshes that are too high-res for volumes (even 500 is quite high).
- DynamicMeshToVolume now emits polygroup-faces that contain holes (ie multiple boundary loops) as a set of triangles, rather than emitting separate overlapping faces for each boundary loop
#rb none
#rnx
#jira none
#preflight 60ba50632c42ea0001cb54c5
[CL 16561742 by Ryan Schmidt in ue5-main branch]
2021-06-04 16:04:03 -04:00
OutputTypeProperties = NewObject < UCreateMeshObjectTypeProperties > ( this ) ;
OutputTypeProperties - > RestoreProperties ( this ) ;
OutputTypeProperties - > InitializeDefault ( ) ;
OutputTypeProperties - > WatchProperty ( OutputTypeProperties - > OutputType , [ this ] ( FString ) { OutputTypeProperties - > UpdatePropertyVisibility ( ) ; } ) ;
AddToolPropertySource ( OutputTypeProperties ) ;
2019-10-01 20:41:42 -04:00
AddToolPropertySource ( ShapeSettings ) ;
ShapeSettings - > RestoreProperties ( this ) ;
MaterialProperties = NewObject < UNewMeshMaterialProperties > ( this ) ;
AddToolPropertySource ( MaterialProperties ) ;
MaterialProperties - > RestoreProperties ( this ) ;
// create preview mesh object
2021-02-24 17:44:12 -04:00
PreviewMesh = NewObject < UPreviewMesh > ( this ) ;
2019-10-01 20:41:42 -04:00
PreviewMesh - > CreateInWorld ( TargetWorld , FTransform : : Identity ) ;
2021-10-07 22:25:54 -04:00
ToolSetupUtil : : ApplyRenderingConfigurationToPreview ( PreviewMesh , nullptr ) ;
2019-10-01 20:41:42 -04:00
PreviewMesh - > SetVisible ( false ) ;
2020-10-09 22:42:26 -04:00
PreviewMesh - > SetMaterial ( MaterialProperties - > Material . Get ( ) ) ;
2021-10-18 14:21:53 -04:00
PreviewMesh - > EnableWireframe ( MaterialProperties - > bShowWireframe ) ;
2019-10-01 20:41:42 -04:00
UpdatePreviewMesh ( ) ;
GetToolManager ( ) - > DisplayMessage (
2021-10-21 17:57:49 -04:00
LOCTEXT ( " OnStartAddPrimitiveTool " , " This Tool creates new shapes. Configure the shape via its settings, position it by moving the mouse in the scene, and drop it as a new object or instance by left-clicking. " ) ,
2019-10-01 20:41:42 -04:00
EToolMessageLevel : : UserNotification ) ;
}
void UAddPrimitiveTool : : Shutdown ( EToolShutdownType ShutdownType )
{
PreviewMesh - > SetVisible ( false ) ;
PreviewMesh - > Disconnect ( ) ;
PreviewMesh = nullptr ;
ModelingTools: add support for creating Volumes directly from DrawPolygon, DrawRevolve, DrawPolyPath, and AddPrimitive, CombineMeshes, CutMeshWithMesh, PlaneCut, BaseCreateFromSelected Tools. Improve support for Editing volumes, eg handling mesh/volume interactions, and add configurable auto-simplification for volumes to avoid painful Editor hangs.
- Move ToolTarget implementations, DynamicMeshToVolume to ModelingComponentsEditorOnly module
- move VolumeToDynamicMesh, DynamicMeshProvider/Commiter interfaces to ModelingComponents module
- Add UCreateMeshObjectTypeProperties property set to expose mesh/volume options
- Add FCreateMeshObjectParams::TypeHintClass to allow AVolume type (or other UClass hints) to be passed to creation APIs
- Add UE::ToolTarget::ConfigureCreateMeshObjectParams() util function in ModelingToolTargetUtil, tries to determine output type in a FCreateMeshObjectParams based on input ToolTarget
- Add UEditorModelingObjectsCreationAPI::CreateVolume() implementation
- Add UEditorModelingObjectsCreationAPI::FilterMaterials() that strips out any internal materials and replaces with WorldGridMaterial. This occurs when (eg) subtracting a Volume from a StaticMesh, because the temporary volume mesh gets assigned internal materials, but the Tools don't know this. Use in EditorModelingObjectsCreationAPI when creating new objects. UStaticMeshComponentToolTarget also does this filtering in ::CommitMaterialSetUpdate().
- Add ::ComponentTypeSupportsCollision() function to ComponentCollisionUtil, use to avoid checks/ensures for Volume targets
- Add support for automatic mesh simplification in DynamicMeshToVolume. Add CVar to VolumeDynamicMeshToolTarget.h to control max triangle count (default 500). Apply auto-simplify when creating or updating an AVolume. This prevents the Editor from blocking for long periods on meshes that are too high-res for volumes (even 500 is quite high).
- DynamicMeshToVolume now emits polygroup-faces that contain holes (ie multiple boundary loops) as a set of triangles, rather than emitting separate overlapping faces for each boundary loop
#rb none
#rnx
#jira none
#preflight 60ba50632c42ea0001cb54c5
[CL 16561742 by Ryan Schmidt in ue5-main branch]
2021-06-04 16:04:03 -04:00
OutputTypeProperties - > SaveProperties ( this ) ;
2019-10-01 20:41:42 -04:00
ShapeSettings - > SaveProperties ( this ) ;
MaterialProperties - > SaveProperties ( this ) ;
}
void UAddPrimitiveTool : : Render ( IToolsContextRenderAPI * RenderAPI )
{
}
2020-01-07 15:54:23 -05:00
void UAddPrimitiveTool : : OnPropertyModified ( UObject * PropertySet , FProperty * Property )
2019-10-01 20:41:42 -04:00
{
2021-01-11 19:45:38 -04:00
// Because of how the ShapeSettings property set is implemented in this Tool, changes to it are transacted,
// and if the user exits the Tool and then tries to undo/redo those transactions, this function will end up being called.
// So we need to ensure that we handle this case.
if ( PreviewMesh )
{
2021-10-18 14:21:53 -04:00
PreviewMesh - > EnableWireframe ( MaterialProperties - > bShowWireframe ) ;
2021-01-11 19:45:38 -04:00
PreviewMesh - > SetMaterial ( MaterialProperties - > Material . Get ( ) ) ;
UpdatePreviewMesh ( ) ;
}
2019-10-01 20:41:42 -04:00
}
FInputRayHit UAddPrimitiveTool : : BeginHoverSequenceHitTest ( const FInputDeviceRay & PressPos )
{
return FInputRayHit ( 0.0f ) ; // always hit in hover
}
void UAddPrimitiveTool : : OnBeginHover ( const FInputDeviceRay & DevicePos )
{
UpdatePreviewPosition ( DevicePos ) ;
}
bool UAddPrimitiveTool : : OnUpdateHover ( const FInputDeviceRay & DevicePos )
{
UpdatePreviewPosition ( DevicePos ) ;
return true ;
}
void UAddPrimitiveTool : : OnEndHover ( )
{
// do nothing
}
void UAddPrimitiveTool : : UpdatePreviewPosition ( const FInputDeviceRay & DeviceClickPos )
{
FRay ClickPosWorldRay = DeviceClickPos . WorldRay ;
// hit position (temp)
bool bHit = false ;
2020-10-22 19:19:16 -04:00
FPlane DrawPlane ( FVector : : ZeroVector , FVector ( 0 , 0 , 1 ) ) ;
2021-10-18 14:21:53 -04:00
if ( ShapeSettings - > TargetSurface = = EMakeMeshPlacementType : : GroundPlane )
2019-10-01 20:41:42 -04:00
{
2021-10-18 14:21:53 -04:00
FVector3f DrawPlanePos = FMath : : RayPlaneIntersection ( ClickPosWorldRay . Origin , ClickPosWorldRay . Direction , DrawPlane ) ;
2019-10-01 20:41:42 -04:00
bHit = true ;
ShapeFrame = FFrame3f ( DrawPlanePos ) ;
}
else
{
// cast ray into scene
FHitResult Result ;
2021-12-09 14:46:09 -05:00
bHit = ToolSceneQueriesUtil : : FindNearestVisibleObjectHit ( this , Result , ClickPosWorldRay ) ;
2019-10-01 20:41:42 -04:00
if ( bHit )
{
2021-10-18 14:21:53 -04:00
FVector3f Normal = Result . ImpactNormal ;
if ( ! ShapeSettings - > bAlignToNormal )
2019-10-24 04:22:13 -04:00
{
Normal = FVector3f : : UnitZ ( ) ;
}
2021-10-18 14:21:53 -04:00
ShapeFrame = FFrame3f ( Result . ImpactPoint , Normal ) ;
2019-10-01 20:41:42 -04:00
ShapeFrame . ConstrainedAlignPerpAxes ( ) ;
}
2020-10-22 19:19:16 -04:00
else
{
// fall back to ground plane if we don't have a scene hit
2021-10-18 14:21:53 -04:00
FVector3f DrawPlanePos = FMath : : RayPlaneIntersection ( ClickPosWorldRay . Origin , ClickPosWorldRay . Direction , DrawPlane ) ;
2020-10-22 19:19:16 -04:00
bHit = true ;
ShapeFrame = FFrame3f ( DrawPlanePos ) ;
}
2019-10-01 20:41:42 -04:00
}
2020-06-23 18:40:00 -04:00
// Snap to grid if applicable
2021-04-06 19:51:47 -04:00
if ( ShapeSettings - > bSnapToGrid )
2020-06-23 18:40:00 -04:00
{
2021-10-21 16:57:00 -04:00
USceneSnappingManager * SnapManager = USceneSnappingManager : : Find ( GetToolManager ( ) ) ;
if ( SnapManager )
2020-06-23 18:40:00 -04:00
{
2021-10-21 16:57:00 -04:00
FSceneSnapQueryRequest Request ;
Request . RequestType = ESceneSnapQueryType : : Position ;
Request . TargetTypes = ESceneSnapQueryTargetType : : Grid ;
Request . Position = ShapeFrame . Origin ;
TArray < FSceneSnapQueryResult > Results ;
if ( SnapManager - > ExecuteSceneSnapQuery ( Request , Results ) )
{
ShapeFrame . Origin = Results [ 0 ] . Position ;
}
2020-06-23 18:40:00 -04:00
}
}
2019-10-01 20:41:42 -04:00
if ( ShapeSettings - > Rotation ! = 0 )
{
ShapeFrame . Rotate ( FQuaternionf ( ShapeFrame . Z ( ) , ShapeSettings - > Rotation , true ) ) ;
}
if ( bHit )
{
PreviewMesh - > SetVisible ( true ) ;
PreviewMesh - > SetTransform ( ShapeFrame . ToFTransform ( ) ) ;
}
else
{
PreviewMesh - > SetVisible ( false ) ;
}
}
2021-10-18 14:21:53 -04:00
void UAddPrimitiveTool : : UpdatePreviewMesh ( ) const
2019-10-01 20:41:42 -04:00
{
FDynamicMesh3 NewMesh ;
2020-04-18 18:42:59 -04:00
GenerateMesh ( & NewMesh ) ;
2019-10-01 20:41:42 -04:00
2021-10-21 17:57:49 -04:00
if ( ShapeSettings - > PolygroupMode = = EMakeMeshPolygroupMode : : PerShape )
2020-03-10 16:54:55 -04:00
{
FaceGroupUtil : : SetGroupID ( NewMesh , 0 ) ;
}
2019-10-01 20:41:42 -04:00
if ( MaterialProperties - > UVScale ! = 1.0 | | MaterialProperties - > bWorldSpaceUVScale )
{
FDynamicMeshEditor Editor ( & NewMesh ) ;
2021-10-18 14:21:53 -04:00
const float WorldUnitsInMetersFactor = MaterialProperties - > bWorldSpaceUVScale ? .01f : 1.0f ;
2019-10-01 20:41:42 -04:00
Editor . RescaleAttributeUVs ( MaterialProperties - > UVScale * WorldUnitsInMetersFactor , MaterialProperties - > bWorldSpaceUVScale ) ;
}
// set mesh position
2021-10-18 14:21:53 -04:00
const FAxisAlignedBox3d Bounds = NewMesh . GetBounds ( true ) ;
2019-10-01 20:41:42 -04:00
FVector3d TargetOrigin = Bounds . Center ( ) ;
if ( ShapeSettings - > PivotLocation = = EMakeMeshPivotLocation : : Base )
{
TargetOrigin . Z = Bounds . Min . Z ;
}
2019-10-24 04:22:13 -04:00
else if ( ShapeSettings - > PivotLocation = = EMakeMeshPivotLocation : : Top )
{
TargetOrigin . Z = Bounds . Max . Z ;
}
2021-10-18 14:21:53 -04:00
for ( const int Vid : NewMesh . VertexIndicesItr ( ) )
2019-10-01 20:41:42 -04:00
{
2021-10-18 14:21:53 -04:00
FVector3d Pos = NewMesh . GetVertex ( Vid ) ;
2019-10-01 20:41:42 -04:00
Pos - = TargetOrigin ;
2021-10-18 14:21:53 -04:00
NewMesh . SetVertex ( Vid , Pos ) ;
2019-10-01 20:41:42 -04:00
}
PreviewMesh - > UpdatePreview ( & NewMesh ) ;
2021-10-14 20:20:28 -04:00
PreviewMesh - > SetTangentsMode ( EDynamicMeshComponentTangentsMode : : AutoCalculated ) ;
const bool CalculateTangentsSuccessful = PreviewMesh - > CalculateTangents ( ) ;
checkSlow ( CalculateTangentsSuccessful ) ;
2019-10-01 20:41:42 -04:00
}
2021-10-18 14:21:53 -04:00
void UAddPrimitiveTool : : OnClicked ( const FInputDeviceRay & ClickPos )
2019-10-01 20:41:42 -04:00
{
2019-10-25 20:21:29 -04:00
UMaterialInterface * Material = PreviewMesh - > GetMaterial ( ) ;
2021-06-02 15:58:00 -04:00
if ( ShapeSettings - > bInstanceIfPossible & & LastGenerated ! = nullptr & & IsEquivalentLastGeneratedAsset ( ) )
2019-10-25 20:21:29 -04:00
{
2021-10-21 17:57:49 -04:00
GetToolManager ( ) - > BeginUndoTransaction ( LOCTEXT ( " AddPrimitiveToolTransactionName " , " Add Shape Mesh " ) ) ;
2019-10-25 20:21:29 -04:00
FActorSpawnParameters SpawnParameters ;
SpawnParameters . Template = LastGenerated - > Actor ;
FRotator Rotation ( 0.0f , 0.0f , 0.0f ) ;
AStaticMeshActor * CloneActor = TargetWorld - > SpawnActor < AStaticMeshActor > ( FVector : : ZeroVector , Rotation , SpawnParameters ) ;
// some properties must be manually set on the component because they will not persist reliably through the spawn template (especially if the actor creation was undone)
CloneActor - > GetStaticMeshComponent ( ) - > SetWorldTransform ( PreviewMesh - > GetTransform ( ) ) ;
CloneActor - > GetStaticMeshComponent ( ) - > SetStaticMesh ( LastGenerated - > StaticMesh ) ;
CloneActor - > GetStaticMeshComponent ( ) - > SetMaterial ( 0 , Material ) ;
2021-06-02 15:58:00 -04:00
# if WITH_EDITOR
2019-10-25 20:21:29 -04:00
CloneActor - > SetActorLabel ( LastGenerated - > Label ) ;
2021-06-02 15:58:00 -04:00
# endif
2019-10-25 20:21:29 -04:00
// select newly-created object
ToolSelectionUtil : : SetNewActorSelection ( GetToolManager ( ) , CloneActor ) ;
GetToolManager ( ) - > EndUndoTransaction ( ) ;
return ;
}
2021-06-02 15:58:00 -04:00
LastGenerated = nullptr ;
2019-10-25 20:21:29 -04:00
2019-10-01 20:41:42 -04:00
const FDynamicMesh3 * CurMesh = PreviewMesh - > GetPreviewDynamicMesh ( ) ;
2020-04-18 18:42:59 -04:00
2021-10-21 17:57:49 -04:00
GetToolManager ( ) - > BeginUndoTransaction ( LOCTEXT ( " AddPrimitiveToolTransactionName " , " Add Shape Mesh " ) ) ;
2019-10-01 20:41:42 -04:00
2021-06-02 15:58:00 -04:00
FCreateMeshObjectParams NewMeshObjectParams ;
NewMeshObjectParams . TargetWorld = TargetWorld ;
2021-10-18 14:21:53 -04:00
NewMeshObjectParams . Transform = PreviewMesh - > GetTransform ( ) ;
2021-06-02 15:58:00 -04:00
NewMeshObjectParams . BaseName = AssetName ;
NewMeshObjectParams . Materials . Add ( Material ) ;
NewMeshObjectParams . SetMesh ( CurMesh ) ;
ModelingTools: add support for creating Volumes directly from DrawPolygon, DrawRevolve, DrawPolyPath, and AddPrimitive, CombineMeshes, CutMeshWithMesh, PlaneCut, BaseCreateFromSelected Tools. Improve support for Editing volumes, eg handling mesh/volume interactions, and add configurable auto-simplification for volumes to avoid painful Editor hangs.
- Move ToolTarget implementations, DynamicMeshToVolume to ModelingComponentsEditorOnly module
- move VolumeToDynamicMesh, DynamicMeshProvider/Commiter interfaces to ModelingComponents module
- Add UCreateMeshObjectTypeProperties property set to expose mesh/volume options
- Add FCreateMeshObjectParams::TypeHintClass to allow AVolume type (or other UClass hints) to be passed to creation APIs
- Add UE::ToolTarget::ConfigureCreateMeshObjectParams() util function in ModelingToolTargetUtil, tries to determine output type in a FCreateMeshObjectParams based on input ToolTarget
- Add UEditorModelingObjectsCreationAPI::CreateVolume() implementation
- Add UEditorModelingObjectsCreationAPI::FilterMaterials() that strips out any internal materials and replaces with WorldGridMaterial. This occurs when (eg) subtracting a Volume from a StaticMesh, because the temporary volume mesh gets assigned internal materials, but the Tools don't know this. Use in EditorModelingObjectsCreationAPI when creating new objects. UStaticMeshComponentToolTarget also does this filtering in ::CommitMaterialSetUpdate().
- Add ::ComponentTypeSupportsCollision() function to ComponentCollisionUtil, use to avoid checks/ensures for Volume targets
- Add support for automatic mesh simplification in DynamicMeshToVolume. Add CVar to VolumeDynamicMeshToolTarget.h to control max triangle count (default 500). Apply auto-simplify when creating or updating an AVolume. This prevents the Editor from blocking for long periods on meshes that are too high-res for volumes (even 500 is quite high).
- DynamicMeshToVolume now emits polygroup-faces that contain holes (ie multiple boundary loops) as a set of triangles, rather than emitting separate overlapping faces for each boundary loop
#rb none
#rnx
#jira none
#preflight 60ba50632c42ea0001cb54c5
[CL 16561742 by Ryan Schmidt in ue5-main branch]
2021-06-04 16:04:03 -04:00
OutputTypeProperties - > ConfigureCreateMeshObjectParams ( NewMeshObjectParams ) ;
2021-06-02 15:58:00 -04:00
FCreateMeshObjectResult Result = UE : : Modeling : : CreateMeshObject ( GetToolManager ( ) , MoveTemp ( NewMeshObjectParams ) ) ;
if ( Result . IsOK ( ) )
2020-01-27 20:11:15 -05:00
{
2021-06-02 15:58:00 -04:00
if ( Result . NewActor ! = nullptr )
{
if ( Cast < AStaticMeshActor > ( Result . NewActor ) ! = nullptr )
{
LastGenerated = NewObject < ULastActorInfo > ( this ) ;
LastGenerated - > ShapeSettings = DuplicateObject ( ShapeSettings , nullptr ) ;
LastGenerated - > MaterialProperties = DuplicateObject ( MaterialProperties , nullptr ) ;
LastGenerated - > Actor = Result . NewActor ;
LastGenerated - > StaticMesh = CastChecked < AStaticMeshActor > ( LastGenerated - > Actor ) - > GetStaticMeshComponent ( ) - > GetStaticMesh ( ) ;
# if WITH_EDITOR
LastGenerated - > Label = LastGenerated - > Actor - > GetActorLabel ( ) ;
# endif
}
2019-10-01 20:41:42 -04:00
2021-06-02 15:58:00 -04:00
// select newly-created object
ToolSelectionUtil : : SetNewActorSelection ( GetToolManager ( ) , Result . NewActor ) ;
}
2020-01-27 20:11:15 -05:00
}
2019-10-01 20:41:42 -04:00
GetToolManager ( ) - > EndUndoTransaction ( ) ;
}
2021-02-08 17:02:09 -04:00
UAddBoxPrimitiveTool : : UAddBoxPrimitiveTool ( const FObjectInitializer & ObjectInitializer )
: Super ( ObjectInitializer . SetDefaultSubobjectClass < UProceduralBoxToolProperties > ( TEXT ( " ShapeSettings " ) ) )
{
AssetName = TEXT ( " Box " ) ;
2021-10-18 14:21:53 -04:00
UInteractiveTool : : SetToolDisplayName ( LOCTEXT ( " BoxToolName " , " Create Box " ) ) ;
2021-02-08 17:02:09 -04:00
}
2020-04-18 18:42:59 -04:00
void UAddBoxPrimitiveTool : : GenerateMesh ( FDynamicMesh3 * OutMesh ) const
2019-10-01 20:41:42 -04:00
{
FGridBoxMeshGenerator BoxGen ;
2021-10-18 14:21:53 -04:00
const UProceduralBoxToolProperties * BoxSettings = Cast < UProceduralBoxToolProperties > ( ShapeSettings ) ;
2021-08-26 09:31:28 -04:00
BoxGen . Box = UE : : Geometry : : FOrientedBox3d ( FVector3d : : Zero ( ) , 0.5 * FVector3d ( BoxSettings - > Depth , BoxSettings - > Width , BoxSettings - > Height ) ) ;
2020-10-09 22:42:26 -04:00
BoxGen . EdgeVertices = FIndex3i ( BoxSettings - > DepthSubdivisions + 1 ,
BoxSettings - > WidthSubdivisions + 1 ,
2020-04-18 18:42:59 -04:00
BoxSettings - > HeightSubdivisions + 1 ) ;
2021-10-18 14:21:53 -04:00
BoxGen . bPolygroupPerQuad = ShapeSettings - > PolygroupMode = = EMakeMeshPolygroupMode : : PerQuad ;
2019-10-01 20:41:42 -04:00
BoxGen . Generate ( ) ;
OutMesh - > Copy ( & BoxGen ) ;
}
2021-02-08 17:02:09 -04:00
UAddRectanglePrimitiveTool : : UAddRectanglePrimitiveTool ( const FObjectInitializer & ObjectInitializer )
: Super ( ObjectInitializer . SetDefaultSubobjectClass < UProceduralRectangleToolProperties > ( TEXT ( " ShapeSettings " ) ) )
{
AssetName = TEXT ( " Rectangle " ) ;
2021-10-18 14:21:53 -04:00
UInteractiveTool : : SetToolDisplayName ( LOCTEXT ( " RectToolName " , " Create Rectangle " ) ) ;
2021-02-08 17:02:09 -04:00
}
2020-04-18 18:42:59 -04:00
void UAddRectanglePrimitiveTool : : GenerateMesh ( FDynamicMesh3 * OutMesh ) const
2019-10-01 20:41:42 -04:00
{
2020-04-18 18:42:59 -04:00
auto * RectangleSettings = Cast < UProceduralRectangleToolProperties > ( ShapeSettings ) ;
2021-10-18 14:21:53 -04:00
switch ( RectangleSettings - > RectangleType )
2020-03-10 16:54:55 -04:00
{
2021-03-01 16:52:28 -04:00
case EProceduralRectType : : Rectangle :
2020-03-10 16:54:55 -04:00
{
2021-03-01 16:52:28 -04:00
FRectangleMeshGenerator RectGen ;
RectGen . Width = RectangleSettings - > Depth ;
RectGen . Height = RectangleSettings - > Width ;
RectGen . WidthVertexCount = RectangleSettings - > DepthSubdivisions + 1 ;
RectGen . HeightVertexCount = RectangleSettings - > WidthSubdivisions + 1 ;
2021-11-18 14:37:34 -05:00
RectGen . bSinglePolyGroup = ( ShapeSettings - > PolygroupMode ! = EMakeMeshPolygroupMode : : PerQuad ) ;
2021-03-01 16:52:28 -04:00
RectGen . Generate ( ) ;
OutMesh - > Copy ( & RectGen ) ;
break ;
}
case EProceduralRectType : : RoundedRectangle :
{
FRoundedRectangleMeshGenerator RectGen ;
RectGen . Width = RectangleSettings - > Depth ;
RectGen . Height = RectangleSettings - > Width ;
RectGen . WidthVertexCount = RectangleSettings - > DepthSubdivisions + 1 ;
RectGen . HeightVertexCount = RectangleSettings - > WidthSubdivisions + 1 ;
2021-11-18 14:37:34 -05:00
RectGen . bSinglePolyGroup = ( ShapeSettings - > PolygroupMode ! = EMakeMeshPolygroupMode : : PerQuad ) ;
2021-03-01 16:52:28 -04:00
RectGen . Radius = RectangleSettings - > CornerRadius ;
RectGen . AngleSamples = RectangleSettings - > CornerSlices - 1 ;
RectGen . Generate ( ) ;
OutMesh - > Copy ( & RectGen ) ;
break ;
}
2020-03-10 16:54:55 -04:00
}
2019-10-23 20:14:30 -04:00
}
2021-02-08 17:02:09 -04:00
UAddDiscPrimitiveTool : : UAddDiscPrimitiveTool ( const FObjectInitializer & ObjectInitializer )
: Super ( ObjectInitializer . SetDefaultSubobjectClass < UProceduralDiscToolProperties > ( TEXT ( " ShapeSettings " ) ) )
{
AssetName = TEXT ( " Disc " ) ;
2021-10-18 14:21:53 -04:00
UInteractiveTool : : SetToolDisplayName ( LOCTEXT ( " DiscToolName " , " Create Disc " ) ) ;
2021-02-08 17:02:09 -04:00
}
2020-04-18 18:42:59 -04:00
void UAddDiscPrimitiveTool : : GenerateMesh ( FDynamicMesh3 * OutMesh ) const
2019-10-24 03:25:01 -04:00
{
2021-10-18 14:21:53 -04:00
const UProceduralDiscToolProperties * DiscSettings = Cast < UProceduralDiscToolProperties > ( ShapeSettings ) ;
2021-03-01 16:52:28 -04:00
switch ( DiscSettings - > DiscType )
2020-03-10 16:54:55 -04:00
{
2021-03-01 16:52:28 -04:00
case EProceduralDiscType : : Disc :
2020-03-10 16:54:55 -04:00
{
2021-03-01 16:52:28 -04:00
FDiscMeshGenerator Gen ;
Gen . Radius = DiscSettings - > Radius ;
Gen . AngleSamples = DiscSettings - > RadialSlices ;
Gen . RadialSamples = DiscSettings - > RadialSubdivisions ;
Gen . bSinglePolygroup = ( ShapeSettings - > PolygroupMode ! = EMakeMeshPolygroupMode : : PerQuad ) ;
Gen . Generate ( ) ;
OutMesh - > Copy ( & Gen ) ;
break ;
}
case EProceduralDiscType : : PuncturedDisc :
{
FPuncturedDiscMeshGenerator Gen ;
Gen . Radius = DiscSettings - > Radius ;
Gen . HoleRadius = FMath : : Min ( DiscSettings - > HoleRadius , Gen . Radius * .999f ) ; // hole cannot be bigger than outer radius
Gen . AngleSamples = DiscSettings - > RadialSlices ;
Gen . RadialSamples = DiscSettings - > RadialSubdivisions ;
Gen . bSinglePolygroup = ( ShapeSettings - > PolygroupMode ! = EMakeMeshPolygroupMode : : PerQuad ) ;
Gen . Generate ( ) ;
OutMesh - > Copy ( & Gen ) ;
break ;
}
2020-03-10 16:54:55 -04:00
}
2019-10-24 03:25:01 -04:00
}
2021-02-08 17:02:09 -04:00
UAddTorusPrimitiveTool : : UAddTorusPrimitiveTool ( const FObjectInitializer & ObjectInitializer )
: Super ( ObjectInitializer . SetDefaultSubobjectClass < UProceduralTorusToolProperties > ( TEXT ( " ShapeSettings " ) ) )
{
AssetName = TEXT ( " Torus " ) ;
2021-10-18 14:21:53 -04:00
UInteractiveTool : : SetToolDisplayName ( LOCTEXT ( " TorusToolName " , " Create Torus " ) ) ;
2021-02-08 17:02:09 -04:00
}
2020-04-18 18:42:59 -04:00
void UAddTorusPrimitiveTool : : GenerateMesh ( FDynamicMesh3 * OutMesh ) const
2019-10-24 20:22:11 -04:00
{
FGeneralizedCylinderGenerator Gen ;
2021-10-18 14:21:53 -04:00
const UProceduralTorusToolProperties * TorusSettings = Cast < UProceduralTorusToolProperties > ( ShapeSettings ) ;
Gen . CrossSection = FPolygon2d : : MakeCircle ( TorusSettings - > MinorRadius , TorusSettings - > MinorSlices ) ;
FPolygon2d PathCircle = FPolygon2d : : MakeCircle ( TorusSettings - > MajorRadius , TorusSettings - > MajorSlices ) ;
2019-10-24 20:22:11 -04:00
for ( int Idx = 0 ; Idx < PathCircle . VertexCount ( ) ; Idx + + )
{
2021-03-30 21:25:22 -04:00
Gen . Path . Add ( FVector3d ( PathCircle [ Idx ] . X , PathCircle [ Idx ] . Y , 0 ) ) ;
2019-10-24 20:22:11 -04:00
}
Gen . bLoop = true ;
Gen . bCapped = false ;
2021-10-18 14:21:53 -04:00
Gen . bPolygroupPerQuad = ShapeSettings - > PolygroupMode = = EMakeMeshPolygroupMode : : PerQuad ;
2019-10-24 20:22:11 -04:00
Gen . InitialFrame = FFrame3d ( Gen . Path [ 0 ] ) ;
Gen . Generate ( ) ;
OutMesh - > Copy ( & Gen ) ;
}
2021-02-08 17:02:09 -04:00
UAddCylinderPrimitiveTool : : UAddCylinderPrimitiveTool ( const FObjectInitializer & ObjectInitializer )
: Super ( ObjectInitializer . SetDefaultSubobjectClass < UProceduralCylinderToolProperties > ( TEXT ( " ShapeSettings " ) ) )
{
AssetName = TEXT ( " Cylinder " ) ;
2021-10-18 14:21:53 -04:00
UInteractiveTool : : SetToolDisplayName ( LOCTEXT ( " CylinderToolName " , " Create Cylinder " ) ) ;
2021-02-08 17:02:09 -04:00
}
2020-04-18 18:42:59 -04:00
void UAddCylinderPrimitiveTool : : GenerateMesh ( FDynamicMesh3 * OutMesh ) const
2019-10-01 20:41:42 -04:00
{
FCylinderGenerator CylGen ;
2021-10-18 14:21:53 -04:00
const UProceduralCylinderToolProperties * CylinderSettings = Cast < UProceduralCylinderToolProperties > ( ShapeSettings ) ;
2020-04-18 18:42:59 -04:00
CylGen . Radius [ 1 ] = CylGen . Radius [ 0 ] = CylinderSettings - > Radius ;
CylGen . Height = CylinderSettings - > Height ;
CylGen . AngleSamples = CylinderSettings - > RadialSlices ;
CylGen . LengthSamples = CylinderSettings - > HeightSubdivisions - 1 ;
2019-10-01 20:41:42 -04:00
CylGen . bCapped = true ;
2021-10-18 14:21:53 -04:00
CylGen . bPolygroupPerQuad = ShapeSettings - > PolygroupMode = = EMakeMeshPolygroupMode : : PerQuad ;
2019-10-01 20:41:42 -04:00
CylGen . Generate ( ) ;
OutMesh - > Copy ( & CylGen ) ;
}
2021-02-08 17:02:09 -04:00
UAddConePrimitiveTool : : UAddConePrimitiveTool ( const FObjectInitializer & ObjectInitializer )
: Super ( ObjectInitializer . SetDefaultSubobjectClass < UProceduralConeToolProperties > ( TEXT ( " ShapeSettings " ) ) )
{
AssetName = TEXT ( " Cone " ) ;
2021-10-18 14:21:53 -04:00
UInteractiveTool : : SetToolDisplayName ( LOCTEXT ( " ConeToolName " , " Create Cone " ) ) ;
2021-02-08 17:02:09 -04:00
}
2020-04-18 18:42:59 -04:00
void UAddConePrimitiveTool : : GenerateMesh ( FDynamicMesh3 * OutMesh ) const
2019-10-01 20:41:42 -04:00
{
// Unreal's standard cone is just a cylinder with a very small top
FCylinderGenerator CylGen ;
2021-10-18 14:21:53 -04:00
const UProceduralConeToolProperties * ConeSettings = Cast < UProceduralConeToolProperties > ( ShapeSettings ) ;
2020-04-18 18:42:59 -04:00
CylGen . Radius [ 0 ] = ConeSettings - > Radius ;
2019-10-01 20:41:42 -04:00
CylGen . Radius [ 1 ] = .01 ;
2020-04-18 18:42:59 -04:00
CylGen . Height = ConeSettings - > Height ;
CylGen . AngleSamples = ConeSettings - > RadialSlices ;
CylGen . LengthSamples = ConeSettings - > HeightSubdivisions - 1 ;
2019-10-01 20:41:42 -04:00
CylGen . bCapped = true ;
2021-10-18 14:21:53 -04:00
CylGen . bPolygroupPerQuad = ShapeSettings - > PolygroupMode = = EMakeMeshPolygroupMode : : PerQuad ;
2019-10-01 20:41:42 -04:00
CylGen . Generate ( ) ;
OutMesh - > Copy ( & CylGen ) ;
}
2021-02-08 17:02:09 -04:00
UAddArrowPrimitiveTool : : UAddArrowPrimitiveTool ( const FObjectInitializer & ObjectInitializer )
: Super ( ObjectInitializer . SetDefaultSubobjectClass < UProceduralArrowToolProperties > ( TEXT ( " ShapeSettings " ) ) )
{
AssetName = TEXT ( " Arrow " ) ;
2021-10-18 14:21:53 -04:00
UInteractiveTool : : SetToolDisplayName ( LOCTEXT ( " ArrowToolName " , " Create Arrow " ) ) ;
2021-02-08 17:02:09 -04:00
}
2020-04-18 18:42:59 -04:00
void UAddArrowPrimitiveTool : : GenerateMesh ( FDynamicMesh3 * OutMesh ) const
2019-10-23 02:11:43 -04:00
{
FArrowGenerator ArrowGen ;
2021-10-18 14:21:53 -04:00
const UProceduralArrowToolProperties * ArrowSettings = Cast < UProceduralArrowToolProperties > ( ShapeSettings ) ;
2020-04-18 18:42:59 -04:00
ArrowGen . StickRadius = ArrowSettings - > ShaftRadius ;
ArrowGen . StickLength = ArrowSettings - > ShaftHeight ;
ArrowGen . HeadBaseRadius = ArrowSettings - > HeadRadius ;
ArrowGen . HeadTipRadius = .01f ;
ArrowGen . HeadLength = ArrowSettings - > HeadHeight ;
ArrowGen . AngleSamples = ArrowSettings - > RadialSlices ;
2019-10-23 02:11:43 -04:00
ArrowGen . bCapped = true ;
2021-10-18 14:21:53 -04:00
ArrowGen . bPolygroupPerQuad = ShapeSettings - > PolygroupMode = = EMakeMeshPolygroupMode : : PerQuad ;
if ( ArrowSettings - > HeightSubdivisions > 1 )
2020-03-10 16:54:55 -04:00
{
2021-10-18 14:21:53 -04:00
const int AdditionalLengthsSamples = ArrowSettings - > HeightSubdivisions - 1 ;
ArrowGen . AdditionalLengthSamples [ 0 ] = AdditionalLengthsSamples ;
ArrowGen . AdditionalLengthSamples [ 1 ] = AdditionalLengthsSamples ;
ArrowGen . AdditionalLengthSamples [ 2 ] = AdditionalLengthsSamples ;
2020-03-10 16:54:55 -04:00
}
2019-10-23 02:11:43 -04:00
ArrowGen . Generate ( ) ;
OutMesh - > Copy ( & ArrowGen ) ;
}
2021-02-08 17:02:09 -04:00
UAddSpherePrimitiveTool : : UAddSpherePrimitiveTool ( const FObjectInitializer & ObjectInitializer )
: Super ( ObjectInitializer . SetDefaultSubobjectClass < UProceduralSphereToolProperties > ( TEXT ( " ShapeSettings " ) ) )
{
2021-08-17 09:50:06 -04:00
AssetName = TEXT ( " Sphere " ) ;
2021-10-18 14:21:53 -04:00
UInteractiveTool : : SetToolDisplayName ( LOCTEXT ( " SphereToolName " , " Create Sphere " ) ) ;
2021-02-08 17:02:09 -04:00
}
2020-04-18 18:42:59 -04:00
void UAddSpherePrimitiveTool : : GenerateMesh ( FDynamicMesh3 * OutMesh ) const
2019-10-01 20:41:42 -04:00
{
2021-10-18 14:21:53 -04:00
const UProceduralSphereToolProperties * SphereSettings = Cast < UProceduralSphereToolProperties > ( ShapeSettings ) ;
2021-10-21 17:57:49 -04:00
switch ( SphereSettings - > SubdivisionType )
2020-03-10 16:54:55 -04:00
{
2021-03-01 16:52:28 -04:00
case EProceduralSphereType : : LatLong :
2020-03-10 16:54:55 -04:00
{
2021-03-01 16:52:28 -04:00
FSphereGenerator SphereGen ;
SphereGen . Radius = SphereSettings - > Radius ;
2021-10-18 14:21:53 -04:00
SphereGen . NumTheta = SphereSettings - > VerticalSlices + 1 ;
SphereGen . NumPhi = SphereSettings - > HorizontalSlices + 1 ;
2021-03-01 16:52:28 -04:00
SphereGen . bPolygroupPerQuad = ( ShapeSettings - > PolygroupMode = = EMakeMeshPolygroupMode : : PerQuad ) ;
SphereGen . Generate ( ) ;
OutMesh - > Copy ( & SphereGen ) ;
break ;
}
case EProceduralSphereType : : Box :
{
FBoxSphereGenerator SphereGen ;
SphereGen . Radius = SphereSettings - > Radius ;
2021-10-18 14:21:53 -04:00
SphereGen . Box = FOrientedBox3d ( FVector3d : : Zero ( ) ,
2021-03-01 16:52:28 -04:00
0.5 * FVector3d ( SphereSettings - > Subdivisions + 1 ,
SphereSettings - > Subdivisions + 1 ,
SphereSettings - > Subdivisions + 1 ) ) ;
int EdgeNum = SphereSettings - > Subdivisions + 1 ;
SphereGen . EdgeVertices = FIndex3i ( EdgeNum , EdgeNum , EdgeNum ) ;
SphereGen . bPolygroupPerQuad = ( ShapeSettings - > PolygroupMode = = EMakeMeshPolygroupMode : : PerQuad ) ;
SphereGen . Generate ( ) ;
OutMesh - > Copy ( & SphereGen ) ;
break ;
}
2020-03-10 16:54:55 -04:00
}
2019-10-21 20:08:02 -04:00
}
2021-03-01 16:52:28 -04:00
2021-02-25 13:48:43 -04:00
UAddStairsPrimitiveTool : : UAddStairsPrimitiveTool ( const FObjectInitializer & ObjectInitializer )
: Super ( ObjectInitializer . SetDefaultSubobjectClass < UProceduralStairsToolProperties > ( TEXT ( " ShapeSettings " ) ) )
2021-02-17 10:26:34 -04:00
{
2021-02-25 13:48:43 -04:00
AssetName = TEXT ( " Stairs " ) ;
2021-10-18 14:21:53 -04:00
UInteractiveTool : : SetToolDisplayName ( LOCTEXT ( " StairsToolName " , " Create Stairs " ) ) ;
2021-02-17 10:26:34 -04:00
}
2021-02-25 13:48:43 -04:00
void UAddStairsPrimitiveTool : : GenerateMesh ( FDynamicMesh3 * OutMesh ) const
2021-02-17 10:26:34 -04:00
{
2021-10-18 14:21:53 -04:00
const UProceduralStairsToolProperties * StairSettings = Cast < UProceduralStairsToolProperties > ( ShapeSettings ) ;
2021-02-25 13:48:43 -04:00
switch ( StairSettings - > StairsType )
{
case EProceduralStairsType : : Linear :
{
FLinearStairGenerator StairGen ;
StairGen . StepWidth = StairSettings - > StepWidth ;
StairGen . StepHeight = StairSettings - > StepHeight ;
StairGen . StepDepth = StairSettings - > StepDepth ;
StairGen . NumSteps = StairSettings - > NumSteps ;
StairGen . bPolygroupPerQuad = ( ShapeSettings - > PolygroupMode = = EMakeMeshPolygroupMode : : PerQuad ) ;
StairGen . Generate ( ) ;
OutMesh - > Copy ( & StairGen ) ;
break ;
}
2021-03-15 14:31:53 -04:00
case EProceduralStairsType : : Floating :
{
FFloatingStairGenerator StairGen ;
StairGen . StepWidth = StairSettings - > StepWidth ;
StairGen . StepHeight = StairSettings - > StepHeight ;
StairGen . StepDepth = StairSettings - > StepDepth ;
StairGen . NumSteps = StairSettings - > NumSteps ;
StairGen . bPolygroupPerQuad = ( ShapeSettings - > PolygroupMode = = EMakeMeshPolygroupMode : : PerQuad ) ;
StairGen . Generate ( ) ;
OutMesh - > Copy ( & StairGen ) ;
break ;
}
2021-02-25 13:48:43 -04:00
case EProceduralStairsType : : Curved :
{
FCurvedStairGenerator StairGen ;
StairGen . StepWidth = StairSettings - > StepWidth ;
StairGen . StepHeight = StairSettings - > StepHeight ;
StairGen . NumSteps = StairSettings - > NumSteps ;
StairGen . InnerRadius = StairSettings - > InnerRadius ;
StairGen . CurveAngle = StairSettings - > CurveAngle ;
StairGen . bPolygroupPerQuad = ( ShapeSettings - > PolygroupMode = = EMakeMeshPolygroupMode : : PerQuad ) ;
StairGen . Generate ( ) ;
OutMesh - > Copy ( & StairGen ) ;
break ;
}
2021-03-15 14:31:53 -04:00
case EProceduralStairsType : : Spiral :
{
FSpiralStairGenerator StairGen ;
StairGen . StepWidth = StairSettings - > StepWidth ;
StairGen . StepHeight = StairSettings - > StepHeight ;
StairGen . NumSteps = StairSettings - > NumSteps ;
StairGen . InnerRadius = StairSettings - > InnerRadius ;
StairGen . CurveAngle = StairSettings - > SpiralAngle ;
StairGen . bPolygroupPerQuad = ( ShapeSettings - > PolygroupMode = = EMakeMeshPolygroupMode : : PerQuad ) ;
StairGen . Generate ( ) ;
OutMesh - > Copy ( & StairGen ) ;
break ;
}
2021-02-25 13:48:43 -04:00
}
2021-02-17 10:26:34 -04:00
}
2021-02-25 13:48:43 -04:00
2019-10-01 20:41:42 -04:00
# undef LOCTEXT_NAMESPACE