Merge branch 'CuttingImprovements' into develop
This commit is contained in:
+11
-4
@@ -235,7 +235,8 @@ elseif BEAM.FLAG == 9 then
|
||||
|
||||
local Part = {}
|
||||
Part.id = EgtGetParent( EgtGetParent( BEAM.FEATUREID))
|
||||
Part.b3Part = EgtGetBBoxGlob( EgtGetFirstNameInGroup( Part.id, 'Box') or GDB_ID.NULL, GDB_BB.STANDARD)
|
||||
Part.idBoxTm = EgtGetFirstInGroup( EgtGetFirstNameInGroup( Part.id, 'Box') or GDB_ID.NULL)
|
||||
Part.b3Part = EgtGetBBoxGlob( Part.idBoxTm, GDB_BB.STANDARD)
|
||||
|
||||
local Proc = FeatureLib.GetProcFromTrimesh( BEAM.FEATUREID, Part)
|
||||
Proc.nGrp = EgtGetInfo( Proc.id, 'GRP', 'i')
|
||||
@@ -573,7 +574,8 @@ if bToProcess then
|
||||
PARTS[i].dRawWidth = PARTS[i].b3Raw:getDimY()
|
||||
PARTS[i].dRawHeight = PARTS[i].b3Raw:getDimZ()
|
||||
-- dimensione pezzo finito
|
||||
PARTS[i].b3Part = EgtGetBBoxGlob( EgtGetFirstNameInGroup( PARTS[i].id, 'Box') or GDB_ID.NULL, GDB_BB.STANDARD)
|
||||
PARTS[i].idBoxTm = EgtGetFirstInGroup( EgtGetFirstNameInGroup( PARTS[i].id, 'Box') or GDB_ID.NULL)
|
||||
PARTS[i].b3Part = EgtGetBBoxGlob( PARTS[i].idBoxTm, GDB_BB.STANDARD)
|
||||
PARTS[i].dLength = PARTS[i].b3Part:getDimX()
|
||||
PARTS[i].dWidth = PARTS[i].b3Part:getDimY()
|
||||
PARTS[i].dHeight = PARTS[i].b3Part:getDimZ()
|
||||
@@ -670,8 +672,13 @@ if bToProcess then
|
||||
sMsg = string.gsub( sMsg or '', '\r', ' ', 10)
|
||||
-- trovata almeno una strategia e feature lavorata completamente
|
||||
if RESULT[i].sType == 'Feature' and RESULT[i].ChosenStrategy.sStatus == 'Completed' then
|
||||
BEAM.ERR = 0
|
||||
BEAM.MSG = '---'
|
||||
if #EgtTrim( sMsg) > 0 then
|
||||
BEAM.ERR = -19
|
||||
BEAM.MSG = sMsg
|
||||
else
|
||||
BEAM.ERR = 0
|
||||
BEAM.MSG = '---'
|
||||
end
|
||||
BEAM.ROT = -( RESULT[i].nRotation or 1) + 1
|
||||
BEAM.CUTID = RESULT[i].idCut
|
||||
BEAM.TASKID = RESULT[i].idTask
|
||||
|
||||
+16
-25
@@ -477,7 +477,8 @@ function BeamExec.ProcessBeams( dRawW, dRawH, dRawL, dOvmHead, dOvmMid, PARTS, b
|
||||
PARTS[i].dWidth = PARTS[i].b3Raw:getDimY()
|
||||
PARTS[i].dHeight = PARTS[i].b3Raw:getDimZ()
|
||||
PARTS[i].bSquareSection = abs( PARTS[i].dWidth - PARTS[i].dHeight) < 100 * GEO.EPS_SMALL
|
||||
PARTS[i].b3Part = EgtGetBBoxGlob( EgtGetFirstNameInGroup( PARTS[i].id, 'Box') or GDB_ID.NULL, GDB_BB.STANDARD)
|
||||
PARTS[i].idBoxTm = EgtGetFirstInGroup( EgtGetFirstNameInGroup( PARTS[i].id, 'Box') or GDB_ID.NULL)
|
||||
PARTS[i].b3Part = EgtGetBBoxGlob( PARTS[i].idBoxTm, GDB_BB.STANDARD)
|
||||
PARTS[i].nIndexInParts = i
|
||||
PARTS[i].SplittingPoints = BeamLib.GetPartSplittingPoints( PARTS[i])
|
||||
PARTS[i].NotClampableLength = { STD = { dHead = 0, dTail = 0}, SIDE = { dHead = 0, dTail = 0}, DOWN = { dHead = 0, dTail = 0}}
|
||||
@@ -715,6 +716,7 @@ local function AreDrillingsMirrored( Proc, ProcMirror, Part)
|
||||
if AreOppositeVectorApprox( vtExtr, vtExtrMirror) then
|
||||
-- fori lungo Y
|
||||
-- per macchine tipo PF il foro principale è sul lato back, per macchine tipo PF1250 è sul lato front
|
||||
-- TODO eliminare i riferimenti a DOWN_HEAD e TWO_EQUAL_HEADS e sostituirli con check iniziale sulla disponibilità di teste?
|
||||
if ( BeamData.TWO_EQUAL_HEADS and AreSameVectorApprox( vtExtr, Y_AX())) or
|
||||
( BeamData.DOWN_HEAD and AreOppositeVectorApprox( vtExtr, Y_AX())) then
|
||||
nDouble = 2
|
||||
@@ -791,6 +793,7 @@ local function GetFeatureInfoAndDependency( vProcSingleRot, Part)
|
||||
Proc.bPassedByHole = true
|
||||
end
|
||||
-- verifiche per specchiature
|
||||
-- TODO eliminare i riferimenti a DOWN_HEAD e TWO_EQUAL_HEADS e sostituirli con check iniziale sulla disponibilità di teste?
|
||||
if BeamData.DOWN_HEAD or BeamData.TWO_EQUAL_HEADS then
|
||||
-- forature
|
||||
if BeamData.DOUBLE_HEAD_DRILLING and ID.IsDrill( Proc) and ID.IsDrill( ProcB) and not Proc.Mirror then
|
||||
@@ -1145,7 +1148,7 @@ local function CalculateMachinings( vProc, Part, nInitialRotation)
|
||||
end
|
||||
-- aggiorno info pezzo
|
||||
Part.b3Raw = EgtGetRawPartBBox( Part.idRaw)
|
||||
Part.b3Part = EgtGetBBoxGlob( EgtGetFirstNameInGroup( Part.id, 'Box') or GDB_ID.NULL, GDB_BB.STANDARD)
|
||||
Part.b3Part = EgtGetBBoxGlob( Part.idBoxTm, GDB_BB.STANDARD)
|
||||
-- si applicano le strategie
|
||||
if Proc.ChosenStrategy then
|
||||
-- carico file script strategia (non serve verificare presenza del file perchè già fatto durante scelta strategia)
|
||||
@@ -1171,7 +1174,7 @@ local function CalculateMachinings( vProc, Part, nInitialRotation)
|
||||
BeamLib.RotateRawPart( Part, 1 - nCurrRotation)
|
||||
-- aggiorno info pezzo
|
||||
Part.b3Raw = EgtGetRawPartBBox( Part.idRaw)
|
||||
Part.b3Part = EgtGetBBoxGlob( EgtGetFirstNameInGroup( Part.id, 'Box') or GDB_ID.NULL, GDB_BB.STANDARD)
|
||||
Part.b3Part = EgtGetBBoxGlob( Part.idBoxTm, GDB_BB.STANDARD)
|
||||
end
|
||||
return MACHININGS, bAreAllApplyOk
|
||||
end
|
||||
@@ -1204,7 +1207,8 @@ function BeamExec.GetProcessings( PARTS, bCalcBestPieceUnloadPosition)
|
||||
if not PARTS[nPart].id and PARTS[nPart].b3Raw:getDimX() < BeamData.dMinRaw then break end
|
||||
local vProcRot = {}
|
||||
|
||||
local nCycles = EgtIf( bCalcBestPieceUnloadPosition, 2, 1) -- se è prerotazione, oltre al ciclo normale, si devono verificare anche invertiti
|
||||
-- se è prerotazione, oltre al ciclo normale, si devono verificare anche invertiti
|
||||
local nCycles = EgtIf( bCalcBestPieceUnloadPosition and PARTS[nPart].GeneralParameters.GEN_sPiecesLoadingPosition ~= 'BTL_POSITION', 2, 1)
|
||||
-- per ogni inversione
|
||||
for nInvertIndex = 1, nCycles do
|
||||
-- per ogni rotazione
|
||||
@@ -1227,14 +1231,14 @@ function BeamExec.GetProcessings( PARTS, bCalcBestPieceUnloadPosition)
|
||||
BeamLib.RotateRawPart( PARTS[nPart], 1)
|
||||
-- aggiorno info pezzo
|
||||
PARTS[nPart].b3Raw = EgtGetRawPartBBox( PARTS[nPart].idRaw)
|
||||
PARTS[nPart].b3Part = EgtGetBBoxGlob( EgtGetFirstNameInGroup( PARTS[nPart].id, 'Box') or GDB_ID.NULL, GDB_BB.STANDARD)
|
||||
PARTS[nPart].b3Part = EgtGetBBoxGlob( PARTS[nPart].idBoxTm, GDB_BB.STANDARD)
|
||||
end
|
||||
if bCalcBestPieceUnloadPosition then
|
||||
if bCalcBestPieceUnloadPosition and PARTS[nPart].GeneralParameters.GEN_sPiecesLoadingPosition ~= 'BTL_POSITION' then
|
||||
-- inversione pezzo testa-coda
|
||||
BeamLib.InvertRawPart( PARTS[nPart], 2)
|
||||
-- aggiorno info pezzo
|
||||
PARTS[nPart].b3Raw = EgtGetRawPartBBox( PARTS[nPart].idRaw)
|
||||
PARTS[nPart].b3Part = EgtGetBBoxGlob( EgtGetFirstNameInGroup( PARTS[nPart].id, 'Box') or GDB_ID.NULL, GDB_BB.STANDARD)
|
||||
PARTS[nPart].b3Part = EgtGetBBoxGlob( PARTS[nPart].idBoxTm, GDB_BB.STANDARD)
|
||||
end
|
||||
end
|
||||
local Part = {}
|
||||
@@ -1528,7 +1532,7 @@ end
|
||||
function BeamExec.GetCombinationMatrix( PARTS, bCalcBestPieceUnloadPosition)
|
||||
-- ricerca strategia di lavorazione per ogni pezzo e applicazione lavorazioni
|
||||
for nPart = 1, #PARTS do
|
||||
local nCycles = EgtIf( bCalcBestPieceUnloadPosition, 2, 1)
|
||||
local nCycles = EgtIf( bCalcBestPieceUnloadPosition and PARTS[nPart].GeneralParameters.GEN_sPiecesLoadingPosition ~= 'BTL_POSITION', 2, 1)
|
||||
-- per ogni inversione
|
||||
for nInvertIndex = 1, nCycles do
|
||||
-- calcolo della migliore strategia per ogni rotazione del pezzo
|
||||
@@ -1543,14 +1547,14 @@ function BeamExec.GetCombinationMatrix( PARTS, bCalcBestPieceUnloadPosition)
|
||||
BeamLib.RotateRawPart( PARTS[nPart], 1)
|
||||
-- aggiorno info pezzo
|
||||
PARTS[nPart].b3Raw = EgtGetRawPartBBox( PARTS[nPart].idRaw)
|
||||
PARTS[nPart].b3Part = EgtGetBBoxGlob( EgtGetFirstNameInGroup( PARTS[nPart].id, 'Box') or GDB_ID.NULL, GDB_BB.STANDARD)
|
||||
PARTS[nPart].b3Part = EgtGetBBoxGlob( PARTS[nPart].idBoxTm, GDB_BB.STANDARD)
|
||||
end
|
||||
if bCalcBestPieceUnloadPosition then
|
||||
if bCalcBestPieceUnloadPosition and PARTS[nPart].GeneralParameters.GEN_sPiecesLoadingPosition ~= 'BTL_POSITION' then
|
||||
-- inversione del pezzo testa-coda
|
||||
BeamLib.InvertRawPart( PARTS[nPart], 2)
|
||||
-- aggiorno info pezzo
|
||||
PARTS[nPart].b3Raw = EgtGetRawPartBBox( PARTS[nPart].idRaw)
|
||||
PARTS[nPart].b3Part = EgtGetBBoxGlob( EgtGetFirstNameInGroup( PARTS[nPart].id, 'Box') or GDB_ID.NULL, GDB_BB.STANDARD)
|
||||
PARTS[nPart].b3Part = EgtGetBBoxGlob( PARTS[nPart].idBoxTm, GDB_BB.STANDARD)
|
||||
end
|
||||
end
|
||||
end
|
||||
@@ -1702,21 +1706,8 @@ function BeamExec.ProcessMachinings( PARTS)
|
||||
bAllStrategiesApplied = false
|
||||
MACHININGS, bAllStrategiesApplied = CalculateMachinings( vProcHeadTail, PARTS[nPart], MatrixResult.nInitialPosition)
|
||||
|
||||
-- cancellazione entità create ma non usate
|
||||
-- TODO funzione?
|
||||
local idAddGroup = BeamLib.GetAddGroup( PARTS[nPart].id)
|
||||
local idCurrentEntity = EgtGetFirstInGroup( idAddGroup or GDB_ID.NULL)
|
||||
while idCurrentEntity do
|
||||
if EgtGetLevel( idCurrentEntity) == GDB_LV.TEMP then
|
||||
local idEntityToDelete = idCurrentEntity
|
||||
idCurrentEntity = EgtGetNext( idCurrentEntity)
|
||||
EgtErase( idEntityToDelete)
|
||||
else
|
||||
idCurrentEntity = EgtGetNext( idCurrentEntity)
|
||||
end
|
||||
end
|
||||
|
||||
-- ordinamento lavorazioni
|
||||
-- TODO sostituire con sorting Egt
|
||||
-- TODO completare ordinamento. Mancano le dipendenze.
|
||||
-- TODO la FinalizeSorting andrebbe rimossa e usato un sorting che non viola le dipendenze
|
||||
MACHININGS = MachiningLib.PrepareMachiningsForSorting( PARTS[nPart])
|
||||
|
||||
+35
-31
@@ -16,7 +16,7 @@ local BeamData = require( 'BeamData')
|
||||
----------------------------------------------------------------------------------------------------------------------------------------------------
|
||||
-- creo i piani paralleli
|
||||
-- GetParallelPlanes: restituisce un vettore con gli indici delle superfici
|
||||
-- nAddGrpId: il layer
|
||||
-- idAddGroup: il layer
|
||||
-- b3BoxDicing: il grezzo della barra
|
||||
-- ptC: il punto centrale del piano della feature
|
||||
-- vtN: il versore normale del piano della feature
|
||||
@@ -30,7 +30,7 @@ local BeamData = require( 'BeamData')
|
||||
-- vtNCut*: il punto centrale della superfice limitante (se non esistono altre superfici può essere omesso)
|
||||
-- ptCCut1*: il punto centrale della superfice limitante (se non esistono altre superfici può essere omesso)
|
||||
-- vtNCut1*: il punto centrale della superfice limitante (se non esistono altre superfici può essere omesso)
|
||||
local function GetParallelPlanes( nAddGrpId, b3BoxDicing, ptC, vtN, nCopyPlane, dOffset, nStep, Color, dTolerance, bNoTolOnFirstCut, ptCCut, vtNCut, ptCCut1, vtNCut1 )
|
||||
local function GetParallelPlanes( idAddGroup, b3BoxDicing, ptC, vtN, nCopyPlane, dOffset, nStep, Color, dTolerance, bNoTolOnFirstCut, ptCCut, vtNCut, ptCCut1, vtNCut1 )
|
||||
local ptMyCCut
|
||||
local AreaMin = 5*5
|
||||
if ptCCut and vtNCut then
|
||||
@@ -46,7 +46,7 @@ local function GetParallelPlanes( nAddGrpId, b3BoxDicing, ptC, vtN, nCopyPlane,
|
||||
local TabellaTmSurfParallel = {}
|
||||
local i = nCopyPlane
|
||||
while i < nStep do
|
||||
local SurfId = EgtSurfTmPlaneInBBox( nAddGrpId, ptC + ( i * dOffset) * vtN, vtN, b3BoxDicing, GDB_RT.GLOB)
|
||||
local SurfId = EgtSurfTmPlaneInBBox( idAddGroup, ptC + ( i * dOffset) * vtN, vtN, b3BoxDicing, GDB_RT.GLOB)
|
||||
local nFacet = EgtSurfTmFacetCount( SurfId or GDB_ID.NULL)
|
||||
if nFacet == 0 then
|
||||
-- se sono al primo taglio do una possibilità in più di girare
|
||||
@@ -86,11 +86,11 @@ end
|
||||
|
||||
----------------------------------------------------------------------------------------------------------------------------------------------------
|
||||
-- GetOrderedCutTable:
|
||||
-- nAddGrpId: il layer
|
||||
-- idAddGroup: il layer
|
||||
-- TabParallelPlanes: tabella delle superfici dei piani paralleli
|
||||
-- TabOrtoPlanes: tabella delle superfici dei piani ortogonali
|
||||
-- stampo l'ordine dei piani di taglio (prima tagli ortogonali piu' esterni poi taglio parallelo collettivo)
|
||||
local function GetOrderedCutTable( nAddGrpId, TabParallelPlanes, TabOrtoPlanes)
|
||||
local function GetOrderedCutTable( idAddGroup, TabParallelPlanes, TabOrtoPlanes)
|
||||
local StepParallel = #TabParallelPlanes
|
||||
local StepOrto = #TabOrtoPlanes
|
||||
local TabellaOrderParallelCut1 = {}
|
||||
@@ -99,8 +99,8 @@ local function GetOrderedCutTable( nAddGrpId, TabParallelPlanes, TabOrtoPlanes)
|
||||
TabellaOrderParallelCut1[IndexTmP] = {}
|
||||
for IndexOrto=1, StepOrto do
|
||||
local ptOrtoN, vtNOrtoN = EgtSurfTmFacetCenter( TabOrtoPlanes[IndexOrto ], 0, GDB_ID.ROOT)
|
||||
local Copy1Id = EgtCopySurfTmFacet( TabParallelPlanes[IndexTmP], 0, nAddGrpId)
|
||||
local Copy2Id = EgtCopySurfTmFacet( TabParallelPlanes[IndexTmP], 0, nAddGrpId)
|
||||
local Copy1Id = EgtCopySurfTmFacet( TabParallelPlanes[IndexTmP], 0, idAddGroup)
|
||||
local Copy2Id = EgtCopySurfTmFacet( TabParallelPlanes[IndexTmP], 0, idAddGroup)
|
||||
if Copy1Id and ptOrtoN then
|
||||
EgtCutSurfTmPlane( Copy1Id, ptOrtoN, -vtNOrtoN, false, GDB_RT.GLOB)
|
||||
EgtCutSurfTmPlane( Copy2Id, ptOrtoN, vtNOrtoN, false, GDB_RT.GLOB)
|
||||
@@ -134,7 +134,7 @@ end
|
||||
-- vtO: il versore dei piani ortogonali
|
||||
-- dOffsetEff: offset della distanza dal punto centrale
|
||||
-- Verifica se l'asse X del box costruito sopra la superficie è più grande di un certo offset
|
||||
local function GetOrtoCutCenter( FacetId, ptC, vtN, vtO, dOffsetEff, dMinNzDownUp)
|
||||
local function GetOrtoCutCenter( FacetId, ptC, vtN, vtO, dOffsetEff)
|
||||
local FrameLocal = Frame3d( EgtSurfTmFacetCenter( FacetId, 0, GDB_ID.ROOT))
|
||||
EgtSetGridFrame(FrameLocal)
|
||||
local IdAuxLocal = EgtGroup(EgtGetParent( FacetId), FrameLocal)
|
||||
@@ -156,7 +156,7 @@ local function GetOrtoCutCenter( FacetId, ptC, vtN, vtO, dOffsetEff, dMinNzDownU
|
||||
-- TODO si può eliminare questo test dato che vengono verificate già volume e dimensione del cubetto??
|
||||
local dMaxLen = BeamData.MAX_LEN_DICE or 600
|
||||
if dLen < dMaxLen and dWidth < dMaxLen and
|
||||
( dLen < dOffsetEff + 1.0 or dWidth < dOffsetEff + 1.0) and vtN:getZ() > dMinNzDownUp then
|
||||
( dLen < dOffsetEff + 1.0 or dWidth < dOffsetEff + 1.0) then
|
||||
return nil, nil, nil
|
||||
end
|
||||
|
||||
@@ -261,7 +261,7 @@ end
|
||||
-- dOffsetParallel: offset della distanza dal punto centrale
|
||||
-- b3BoxDicing: il grezzo della barra
|
||||
-- Verifica se l'asse X del box costruito sopra le 2 facce è più piccolo di un certo offset e quindi la faccia O è superflua
|
||||
local function VerifyFirstOrthoCut( CutTable, dOffsetParallel, b3BoxDicing, dMinNzDownUp)
|
||||
local function VerifyFirstOrthoCut( CutTable, dOffsetParallel, b3BoxDicing)
|
||||
|
||||
if not CutTable[1] or not CutTable[2] then return end
|
||||
|
||||
@@ -294,9 +294,9 @@ local function VerifyFirstOrthoCut( CutTable, dOffsetParallel, b3BoxDicing, dMin
|
||||
-- lunghezza totale faccia
|
||||
local dLongSize = x1 + x2
|
||||
-- se faccia piccola e non orientata verso il basso, elimino ortogonale e unisco le due parti
|
||||
if dLongSize <= dOffsetParallel + 1.0 and vtN1:getZ() > dMinNzDownUp then
|
||||
local nAddGrpId = EgtGetParent( Cut1Id)
|
||||
local SurfId = EgtSurfTmBySewing( nAddGrpId, { Cut1Id, Cut2Id})
|
||||
if dLongSize <= dOffsetParallel + 1.0 then
|
||||
local idAddGroup = EgtGetParent( Cut1Id)
|
||||
local SurfId = EgtSurfTmBySewing( idAddGroup, { Cut1Id, Cut2Id})
|
||||
--EgtSetColor( SurfId, Color3d( FUCHSIA(), 60))
|
||||
EgtErase( CutOId)
|
||||
table.remove( CutTable[1], 1)
|
||||
@@ -338,7 +338,7 @@ end
|
||||
----------------------------------------------------------------------------------------------------------------------------------------------------
|
||||
-- ricavo l'altezza del BoundingBox assegnati gli estremi del grezzo e la feature
|
||||
-- le funzioni commentate permettono di vedere la creazione di BoundingBox
|
||||
local function DistanzaMassima( nAddGrpId, ptC1, vtN1, ptC2, vtN2, b3BoxDicing, TPoint)
|
||||
local function DistanzaMassima( idAddGroup, ptC1, vtN1, ptC2, vtN2, b3BoxDicing, TPoint)
|
||||
-- calcolo il riferimento nel piano 1
|
||||
local Frame1 = Frame3d( ptC1, vtN1)
|
||||
-- determino l'ingombro in questo riferimento della parte di trave compresa nel o nei piani
|
||||
@@ -353,7 +353,7 @@ local function DistanzaMassima( nAddGrpId, ptC1, vtN1, ptC2, vtN2, b3BoxDicing,
|
||||
end
|
||||
-- eventuale altra faccia
|
||||
if ptC2 and vtN2 then
|
||||
local IdAux = EgtGroup( nAddGrpId)
|
||||
local IdAux = EgtGroup( idAddGroup)
|
||||
local IdSurf2 = EgtSurfTmPlaneInBBox( IdAux, ptC2, vtN2, b3BoxDicing, GDB_RT.GLOB)
|
||||
EgtCutSurfTmPlane( IdSurf2, ptC1, -vtN1, false, GDB_RT.GLOB)
|
||||
if IdSurf2 then
|
||||
@@ -394,7 +394,12 @@ end
|
||||
---------------------------------------------------------------------------------------------------------------
|
||||
function DiceCut.GetDice( Part, Face1, Face2, OptionalParameters)
|
||||
-- gruppo per geometria addizionale
|
||||
local nAddGrpId = BeamLib.GetAddGroup( Part.id)
|
||||
local idAddGroup
|
||||
if OptionalParameters.bSaveAddedGeometries then
|
||||
idAddGroup = BeamLib.GetAddGroup( Part.id)
|
||||
else
|
||||
idAddGroup = BeamLib.GetTempGroup()
|
||||
end
|
||||
|
||||
-- faccia primaria
|
||||
local ptCMainFace
|
||||
@@ -430,8 +435,6 @@ function DiceCut.GetDice( Part, Face1, Face2, OptionalParameters)
|
||||
local nStepOrthogonal = OptionalParameters.nStepOrthogonal or 100
|
||||
-- distanza tra piani paralleli e piani di taglio (era sempre 0, serve???)
|
||||
local dTolerance = OptionalParameters.dTolerance or 0
|
||||
-- inclinazione limite per taglio da sotto
|
||||
local dMinNzDownUp = OptionalParameters.dMinNzDownUp or -2
|
||||
|
||||
--Ricavo le altezze dei BoundingBox contenente feature e estremi del grezzo
|
||||
local TBoxPoint = CalcolaPuntiEstremiBox( b3BoxDicing)
|
||||
@@ -439,14 +442,15 @@ function DiceCut.GetDice( Part, Face1, Face2, OptionalParameters)
|
||||
if ptCSubordinateFace and vtNSubordinateFace then
|
||||
TBoxPoint = VerificaEstremiGrezzo( ptCSubordinateFace, vtNSubordinateFace, TBoxPoint)
|
||||
end
|
||||
local dElevP = DistanzaMassima( nAddGrpId, ptCMainFace, vtNMainFace, ptCSubordinateFace, vtNSubordinateFace, b3BoxDicing, TBoxPoint)
|
||||
local dElevP = DistanzaMassima( idAddGroup, ptCMainFace, vtNMainFace, ptCSubordinateFace, vtNSubordinateFace, b3BoxDicing, TBoxPoint)
|
||||
local dElevO
|
||||
if ptCSubordinateFace and vtNSubordinateFace and not AreOppositeVectorApprox( vtNSubordinateFace, vtNMainFace) then
|
||||
dElevO = DistanzaMassima( nAddGrpId, ptCSubordinateFace, vtNSubordinateFace, ptCMainFace, vtNMainFace, b3BoxDicing, TBoxPoint)
|
||||
dElevO = DistanzaMassima( idAddGroup, ptCSubordinateFace, vtNSubordinateFace, ptCMainFace, vtNMainFace, b3BoxDicing, TBoxPoint)
|
||||
end
|
||||
|
||||
-- TODO parte sotto da aggiungere???? se sì va passata anche la dimensione cubetto ridotta dOffsetOrthogonalReduced
|
||||
-- se non c'è testa da sotto e normali senza componenti in Y con faccia quasi verticale e trave non alta, uso per offset i limiti dei tagli di testa e coda
|
||||
-- TODO eliminare i riferimenti a DOWN_HEAD e TWO_EQUAL_HEADS e sostituirli con check iniziale sulla disponibilità di teste?
|
||||
-- if not BD.TURN and not BD.DOWN_HEAD and abs( vtNPlanes:getY()) < 0.1 and vtNPlanes:getZ() < 0.7071 and ( not vtNBond or abs( vtNBond:getY()) < 0.1) and BBoxRawPart:getDimZ() < BD.MIN_DIM_HBEAM then
|
||||
-- dOffsetOrthogonal = dOffsetOrthogonalReduced
|
||||
-- end
|
||||
@@ -476,7 +480,7 @@ function DiceCut.GetDice( Part, Face1, Face2, OptionalParameters)
|
||||
|
||||
-- PIANI PARALLELI alla faccia di taglio
|
||||
local TabellaTmSurfP = {}
|
||||
local TabFromIn = GetParallelPlanes( nAddGrpId, b3BoxDicing, ptCMainFace, vtNMainFace, 0, dOffsetParallel, nStepParallel, Color3d( FUCHSIA(), 60), dTolerance, true, ptCSubordinateFace, vtNSubordinateFace)
|
||||
local TabFromIn = GetParallelPlanes( idAddGroup, b3BoxDicing, ptCMainFace, vtNMainFace, 0, dOffsetParallel, nStepParallel, Color3d( FUCHSIA(), 60), dTolerance, true, ptCSubordinateFace, vtNSubordinateFace)
|
||||
for i = #TabFromIn, 1, -1 do
|
||||
table.insert( TabellaTmSurfP, TabFromIn[i])
|
||||
end
|
||||
@@ -485,12 +489,12 @@ function DiceCut.GetDice( Part, Face1, Face2, OptionalParameters)
|
||||
-- orientamento definito da seconda faccia
|
||||
if not bGetOrtoPlanes then
|
||||
local TabellaTmSurfOrto = {}
|
||||
local TabFromIn = GetParallelPlanes( nAddGrpId, b3BoxDicing, ptCSubordinateFace, vtNSubordinateFace, 0, dOffsetOrthogonal, nStepOrthogonal, Color3d( GREEN(), 60), dTolerance, false, ptCMainFace, vtNMainFace)
|
||||
local TabFromIn = GetParallelPlanes( idAddGroup, b3BoxDicing, ptCSubordinateFace, vtNSubordinateFace, 0, dOffsetOrthogonal, nStepOrthogonal, Color3d( GREEN(), 60), dTolerance, false, ptCMainFace, vtNMainFace)
|
||||
for i = #TabFromIn, 1, -1 do
|
||||
table.insert( TabellaTmSurfOrto, TabFromIn[i])
|
||||
end
|
||||
local TabellaOrderParallelCut = GetOrderedCutTable( nAddGrpId, TabellaTmSurfP, TabellaTmSurfOrto) -- Ottiene la tabella dei tagli paralleli ordinati
|
||||
local TabellaOrderOrtoCut = GetOrderedCutTable( nAddGrpId, TabellaTmSurfOrto, TabellaTmSurfP) -- Ottiene la tabella dei tagli ortogonali da riordinare per strato
|
||||
local TabellaOrderParallelCut = GetOrderedCutTable( idAddGroup, TabellaTmSurfP, TabellaTmSurfOrto) -- Ottiene la tabella dei tagli paralleli ordinati
|
||||
local TabellaOrderOrtoCut = GetOrderedCutTable( idAddGroup, TabellaTmSurfOrto, TabellaTmSurfP) -- Ottiene la tabella dei tagli ortogonali da riordinare per strato
|
||||
|
||||
TabGREEN = SortOrtoCutsByNormalMethod( TabellaOrderParallelCut, TabellaOrderOrtoCut) -- I tagli ortogonali vengono ordinati per strato
|
||||
TabFUCHSIA = TabellaOrderParallelCut -- I tagli paralleli sono già ordinati
|
||||
@@ -508,10 +512,10 @@ function DiceCut.GetDice( Part, Face1, Face2, OptionalParameters)
|
||||
end
|
||||
-- calcolo la direzione dei piani ortogonali
|
||||
local vtO = VectorFromUprightOrtho( vtNInner)
|
||||
if vtNInner:getZ() > -0.0175 or vtNInner:getZ() < dMinNzDownUp or abs( vtNInner:getY()) > 0.8 then
|
||||
if vtNInner:getZ() > -0.0175 or abs( vtNInner:getY()) > 0.8 then
|
||||
vtO:rotate( vtNInner, 90)
|
||||
-- se diretto troppo ortogonalmente all'asse trave e taglio non da sotto, lo ruoto ulteriormente
|
||||
if ( abs( vtO:getY()) > 4 * abs( vtO:getX()) or b3BoxDicing:getDimZ() > 620) and vtNInner:getZ() > dMinNzDownUp then
|
||||
if ( abs( vtO:getY()) > 4 * abs( vtO:getX()) or b3BoxDicing:getDimZ() > 620) then
|
||||
vtO:rotate( vtNInner, 90)
|
||||
-- se faccia principale verso il basso (almeno -3deg), lo inverto per iniziare da sopra
|
||||
if vtNInner:getZ() < -0.05 then
|
||||
@@ -533,16 +537,16 @@ function DiceCut.GetDice( Part, Face1, Face2, OptionalParameters)
|
||||
-- CopyPlane: 0 => crea la prima faccia direttamente sul punto passato
|
||||
-- CopyPlane: 1 => crea la prima faccia e tutte le altre con l'offset passato
|
||||
-- CopyPlane: 0.5 => crea la prima faccia a metà offset e tutte le altre con l'offest intero
|
||||
local OffsetRel, CopyPlane, dCenOffs, ptCStart = GetOrtoCutCenter( TabellaTmSurfP[PlnInd], ptCInner, vtNInner, vtO, dOffsetOrthogonal, dMinNzDownUp)
|
||||
local OffsetRel, CopyPlane, dCenOffs, ptCStart = GetOrtoCutCenter( TabellaTmSurfP[PlnInd], ptCInner, vtNInner, vtO, dOffsetOrthogonal)
|
||||
|
||||
if OffsetRel and CopyPlane and dCenOffs then
|
||||
ptCInner = ptCInner + dCenOffs * vtO
|
||||
local TabRight = GetParallelPlanes( nAddGrpId, b3BoxDicing, ptCStart, vtO, CopyPlane, -OffsetRel, nStepOrthogonal, Color3d( GREEN(), 60),
|
||||
local TabRight = GetParallelPlanes( idAddGroup, b3BoxDicing, ptCStart, vtO, CopyPlane, -OffsetRel, nStepOrthogonal, Color3d( GREEN(), 60),
|
||||
dTolerance, false, ptCInner, vtNInner, ptCOuter, vtNOuter)
|
||||
if CopyPlane == 0 then
|
||||
CopyPlane = 1
|
||||
end
|
||||
local TabLeft = GetParallelPlanes( nAddGrpId, b3BoxDicing, ptCStart, vtO, CopyPlane, OffsetRel, nStepOrthogonal, Color3d( GREEN(), 60),
|
||||
local TabLeft = GetParallelPlanes( idAddGroup, b3BoxDicing, ptCStart, vtO, CopyPlane, OffsetRel, nStepOrthogonal, Color3d( GREEN(), 60),
|
||||
dTolerance, false, ptCInner, vtNInner, ptCOuter, vtNOuter)
|
||||
-- carico la tabella con gli indici riordinati
|
||||
local TempOrtoTab = {}
|
||||
@@ -553,7 +557,7 @@ function DiceCut.GetDice( Part, Face1, Face2, OptionalParameters)
|
||||
table.insert( TempOrtoTab, TabRight[i])
|
||||
end
|
||||
-- creo una tabella per ogni piano per generare i tagli sulla Inner
|
||||
local TempParTab = GetOrderedCutTable( nAddGrpId, {TabellaTmSurfP[PlnInd]}, TempOrtoTab)
|
||||
local TempParTab = GetOrderedCutTable( idAddGroup, {TabellaTmSurfP[PlnInd]}, TempOrtoTab)
|
||||
for i = 1, #TempParTab do
|
||||
table.insert( TabFUCHSIA, TempParTab[i])
|
||||
end
|
||||
@@ -582,7 +586,7 @@ function DiceCut.GetDice( Part, Face1, Face2, OptionalParameters)
|
||||
|
||||
-- Se esiste la superficie limitante (nFacet == 2) verifica se il taglio più esterno è superfluo e quindi viene eliminato
|
||||
if not bGetOrtoPlanes then
|
||||
VerifyFirstOrthoCut( UltimateTable, dOffsetParallelOriginal, b3BoxDicing, dMinNzDownUp)
|
||||
VerifyFirstOrthoCut( UltimateTable, dOffsetParallelOriginal, b3BoxDicing)
|
||||
-- se rimangono due sole facce, devono coincidere con le originali e quindi sono superflue
|
||||
if #UltimateTable == 2 and #UltimateTable[1] == 1 and #UltimateTable[2] == 1 then
|
||||
EgtErase( UltimateTable[1][1])
|
||||
|
||||
+24
-25
@@ -136,6 +136,8 @@ function FaceData.GetEdgesInfo( ProcOrId, idFace )
|
||||
end
|
||||
CurrentEdge.bIsStartOpen = EdgesEgt[nPreviousEdgeIndex].Open
|
||||
CurrentEdge.bIsEndOpen = EdgesEgt[nNextEdgeIndex].Open
|
||||
CurrentEdge.ptStart = Point3d( EdgesEgt[i].Start)
|
||||
CurrentEdge.ptEnd = Point3d( EdgesEgt[nNextEdgeIndex].Start)
|
||||
CurrentEdge.sType = 'Standard'
|
||||
CurrentEdge.id = i - 1
|
||||
|
||||
@@ -175,10 +177,11 @@ function FaceData.GetFacesInfo( Proc, Part, FacesToGet)
|
||||
for i = 1, Proc.nFct do
|
||||
Faces[i] = {}
|
||||
Faces[i].id = i - 1
|
||||
Faces[i].idTrimesh = Proc.id
|
||||
Faces[i].ptCenter, Faces[i].vtN = EgtSurfTmFacetCenter( Proc.id, i - 1, GDB_ID.ROOT)
|
||||
if Proc.nFct < 6 or FaceIsToGet( i) then
|
||||
-- frame OCS faccia
|
||||
Faces[i].vtFrameHV = Frame3d( Faces[i].ptCenter, Faces[i].vtN)
|
||||
Faces[i].frFrameHV = Frame3d( Faces[i].ptCenter, Faces[i].vtN)
|
||||
-- elevazione calcolata rispetto al box della parte
|
||||
Faces[i].dElevation = EgtSurfTmFacetElevationInBBox( Proc.id, i - 1, Part.b3Part, true, GDB_ID.ROOT)
|
||||
-- TODO qui sarebbe meglio l'area vera e non quella del rettangolo minimo
|
||||
@@ -215,46 +218,40 @@ function FaceData.GetFacesInfo( Proc, Part, FacesToGet)
|
||||
end
|
||||
|
||||
-------------------------------------------------------------------------------------------------------------
|
||||
function FaceData.IsFaceRectangular( Proc, idFace)
|
||||
local nAddGrpId = BeamLib.GetAddGroup( Proc.idPart)
|
||||
local nContourId, nContourCnt = EgtExtractSurfTmFacetLoops( Proc.id, idFace, nAddGrpId)
|
||||
function FaceData.IsFaceRectangle( Face)
|
||||
-- recupero gruppo per geometrie temporanee
|
||||
local idTempGroup = BeamLib.GetTempGroup()
|
||||
|
||||
local nContourId, nContourCnt = EgtExtractSurfTmFacetLoops( Face.idTrimesh, Face.id, idTempGroup)
|
||||
if nContourCnt > 1 then
|
||||
error( 'IsFaceRectangular : too many loops')
|
||||
error( 'IsFaceRectangle : too many loops')
|
||||
end
|
||||
|
||||
local bIsRectangular = EgtCurveIsARectangle( nContourId)
|
||||
|
||||
-- elimino curve create
|
||||
for i = 1, nContourCnt do
|
||||
EgtErase( nContourId + i - 1)
|
||||
end
|
||||
|
||||
return bIsRectangular
|
||||
end
|
||||
|
||||
-------------------------------------------------------------------------------------------------------------
|
||||
function FaceData.IsFaceRhomboid( Proc, idFace)
|
||||
local nAddGrpId = BeamLib.GetAddGroup( Proc.idPart)
|
||||
local nContourId, nContourCnt = EgtExtractSurfTmFacetLoops( Proc.id, idFace, nAddGrpId)
|
||||
function FaceData.IsFaceParallelogram( Face)
|
||||
-- recupero gruppo per geometrie temporanee
|
||||
local idTempGroup = BeamLib.GetTempGroup()
|
||||
|
||||
local nContourId, nContourCnt = EgtExtractSurfTmFacetLoops( Face.idTrimesh, Face.id, idTempGroup)
|
||||
if nContourCnt > 1 then
|
||||
error( 'IsFaceRectangular : too many loops')
|
||||
error( 'IsFaceParallelogram : too many loops')
|
||||
end
|
||||
|
||||
local bIsTrapezoid = EgtCurveIsATrapezoid( nContourId)
|
||||
local bIsRhomboid = false
|
||||
-- un parallelogramma è un trapezoide con i lati paralleli a due a due
|
||||
if bIsTrapezoid
|
||||
and AreOppositeVectorApprox( Proc.Faces[idFace + 1].Edges[1].vtN, Proc.Faces[idFace + 1].Edges[3].vtN)
|
||||
and AreOppositeVectorApprox( Proc.Faces[idFace + 1].Edges[2].vtN, Proc.Faces[idFace + 1].Edges[4].vtN) then
|
||||
and AreOppositeVectorApprox( Face.Edges[1].vtN, Face.Edges[3].vtN)
|
||||
and AreOppositeVectorApprox( Face.Edges[2].vtN, Face.Edges[4].vtN) then
|
||||
|
||||
bIsRhomboid = true
|
||||
end
|
||||
|
||||
-- elimino curve create
|
||||
for i = 1, nContourCnt do
|
||||
EgtErase( nContourId + i - 1)
|
||||
end
|
||||
|
||||
return bIsRhomboid
|
||||
end
|
||||
|
||||
@@ -429,6 +426,8 @@ local function GetBottomFaces( Proc)
|
||||
CurrentEdge.dElevation = BottomFaces[1].Edges[i].dElevation
|
||||
CurrentEdge.bIsStartOpen = BottomFaces[1].Edges[i].bIsStartOpen
|
||||
CurrentEdge.bIsEndOpen = BottomFaces[1].Edges[i].bIsEndOpen
|
||||
CurrentEdge.ptStart = BottomFaces[1].Edges[i].ptStart
|
||||
CurrentEdge.ptEnd = BottomFaces[1].Edges[i].ptEnd
|
||||
|
||||
if nFirstLongEdgeIndex then
|
||||
if i == nFirstLongEdgeIndex then
|
||||
@@ -524,6 +523,8 @@ local function GetLongFaces( Proc, MainFaces)
|
||||
CurrentEdge.dElevation = LongFaces[i].Edges[j].dElevation
|
||||
CurrentEdge.bIsStartOpen = LongFaces[i].Edges[j].bIsStartOpen
|
||||
CurrentEdge.bIsEndOpen = LongFaces[i].Edges[j].bIsEndOpen
|
||||
CurrentEdge.ptStart = LongFaces[i].Edges[j].ptStart
|
||||
CurrentEdge.ptEnd = LongFaces[i].Edges[j].ptEnd
|
||||
|
||||
if Proc.Topology.sFamily == 'Tunnel' then
|
||||
if CurrentEdge.idAdjacentFace > -1 then
|
||||
@@ -620,6 +621,8 @@ local function GetSideFaces( Proc, MainFaces)
|
||||
CurrentEdge.dElevation = SideFaces[i].Edges[j].dElevation
|
||||
CurrentEdge.bIsStartOpen = SideFaces[i].Edges[j].bIsStartOpen
|
||||
CurrentEdge.bIsEndOpen = SideFaces[i].Edges[j].bIsEndOpen
|
||||
CurrentEdge.ptStart = SideFaces[i].Edges[j].ptStart
|
||||
CurrentEdge.ptEnd = SideFaces[i].Edges[j].ptEnd
|
||||
|
||||
if Proc.Topology.sFamily == 'Tunnel' then
|
||||
if CurrentEdge.idAdjacentFace > -1 then
|
||||
@@ -671,10 +674,6 @@ function FaceData.GetMainFaces( Proc, Part)
|
||||
MainFaces.LongFaces = GetLongFaces( Proc, MainFaces)
|
||||
MainFaces.SideFaces = GetSideFaces( Proc, MainFaces)
|
||||
|
||||
-- scrivo informazioni delle facce nel log
|
||||
if EgtGetDebugLevel() >= 3 then
|
||||
Logs.WriteMainFacesLog( Proc, MainFaces)
|
||||
end
|
||||
else
|
||||
MainFaces = nil
|
||||
EgtOutLog( '---MainFaces NOT NEEDED---')
|
||||
|
||||
@@ -323,7 +323,7 @@ function FeatureLib.GetAdditionalInfo( Proc, Part)
|
||||
elseif ID.IsRidgeLap( Proc) then
|
||||
Proc.AdjacencyMatrix = FaceData.GetAdjacencyMatrix( Proc)
|
||||
Proc.Faces = FaceData.GetFacesInfo( Proc, Part)
|
||||
elseif ID.IsMarking( Proc) then
|
||||
elseif ID.IsMarking( Proc) or ID.IsText( Proc) then
|
||||
Proc.FeatureInfo = FeatureLib.GetMarkTextData( Proc)
|
||||
elseif ID.IsHipValleyRafterNotch( Proc) then
|
||||
Proc.AdjacencyMatrix = FaceData.GetAdjacencyMatrix( Proc)
|
||||
|
||||
+208
-24
@@ -267,6 +267,162 @@ local function IsToolInAvailableToolList( AvailableToolList, sTool)
|
||||
return bToolFound
|
||||
end
|
||||
|
||||
-------------------------------------------------------------------------------------------------------------
|
||||
-- in base a tipo testa e angolo soglia, verifica se la faccia è troppo inclinata per la lavorazione scelta (per DownUp passare vtNFace opposta)
|
||||
local function IsFaceZOutOfRange ( vtNFace, Tool)
|
||||
|
||||
-- lama sopra: angolo negativo troppo basso
|
||||
if Tool.SetupInfo.HeadType.bTop and vtNFace:getZ() < Tool.SetupInfo.GetMinNz( vtNFace, Tool) - GEO.EPS_ZERO then
|
||||
return true
|
||||
end
|
||||
-- lama sotto: angolo positivo troppo elevato
|
||||
if Tool.SetupInfo.HeadType.bBottom and vtNFace:getZ() > Tool.SetupInfo.GetMaxNz( vtNFace, Tool) + GEO.EPS_ZERO then
|
||||
return true
|
||||
end
|
||||
|
||||
return false
|
||||
end
|
||||
|
||||
-------------------------------------------------------------------------------------------------------------
|
||||
-- nel piano perpendicolare alla direzione di taglio, se c'è intersezione tra motore e trave c'è collisione
|
||||
local function Check2DBladeCollision( Edge, vtNFace, vtHead, Part, Tool, dDepthToMachine)
|
||||
|
||||
-- se direzione utensile parallela ad uno degli assi principali non serve alcuna verifica
|
||||
if AreSameOrOppositeVectorApprox( Edge.vtN, X_AX())
|
||||
or AreSameOrOppositeVectorApprox( Edge.vtN, Y_AX())
|
||||
or AreSameOrOppositeVectorApprox( Edge.vtN, Z_AX()) then
|
||||
|
||||
return false
|
||||
end
|
||||
|
||||
local idTempGroup = BeamLib.GetTempGroup()
|
||||
|
||||
-- riferimento perpendicolare al taglio, X nel verso della normale al lato e Y verso il motore
|
||||
local ptMachining = Point3d( ( Edge.ptStart + Edge.ptEnd) / 2) + Edge.vtN * ( Edge.dElevation - dDepthToMachine)
|
||||
local vtEdge = Edge.ptEnd - Edge.ptStart
|
||||
vtEdge:normalize()
|
||||
|
||||
-- costruzione flat region del pezzo nel piano perpendicolare al taglio
|
||||
-- si estrae prima la silhouette nel piano
|
||||
local idFirstCurve, nCurveCount = EgtGetSurfTmSilhouette( Part.idBoxTm, vtEdge, 10 * GEO.EPS_SMALL, idTempGroup, GDB_RT.GLOB)
|
||||
-- se più curve c'è qualcosa che non va: errore
|
||||
if nCurveCount > 1 then
|
||||
error( 'Check2DBladeCollision : error in part box')
|
||||
end
|
||||
-- creazione flat region dalla silhouette
|
||||
local idPartSurfFr = EgtSurfFlatRegion( idTempGroup, idFirstCurve)
|
||||
|
||||
-- costruzione flat region del grezzo restante nel piano perpendicolare al taglio
|
||||
-- si costruisce il box in globale
|
||||
local ptRestLengthMax = Point3d( Part.b3Part:getMin() + X_AX() * 500 * GEO.EPS_SMALL)
|
||||
local ptRestLengthMin = Point3d( Part.b3Part:getMin():getX() - 2000, Part.b3Part:getMax():getY(), Part.b3Part:getMax():getZ())
|
||||
local b3RestLength = BBox3d( ptRestLengthMin, ptRestLengthMax)
|
||||
-- si crea la trimesh dal box
|
||||
local idRestLengthBoxTm = EgtSurfTmBBox( idTempGroup, b3RestLength , false, GDB_RT.GLOB)
|
||||
-- si estrae la silhouette nel piano
|
||||
idFirstCurve, nCurveCount = EgtGetSurfTmSilhouette( idRestLengthBoxTm, vtEdge, 10 * GEO.EPS_SMALL, idTempGroup, GDB_RT.GLOB)
|
||||
-- se più curve c'è qualcosa che non va: errore
|
||||
if nCurveCount > 1 then
|
||||
error( 'Check2DBladeCollision : error in part box')
|
||||
end
|
||||
-- creazione flat region dalla silhouette
|
||||
local idRestLengthSurfFr = EgtSurfFlatRegion( idTempGroup, idFirstCurve)
|
||||
|
||||
-- costruzione flat region approssimata del motore nel piano perpendicolare al taglio
|
||||
-- punto di congiunzione tra motore e lama
|
||||
local ptMaxElev = ptMachining + Edge.vtN * Tool.dMaxMaterial
|
||||
-- se taglio standard (no DownUp) il punto va spostato dello spessore lama
|
||||
if AreSameVectorApprox( vtNFace, vtHead) then
|
||||
ptMaxElev = ptMaxElev + vtNFace * Tool.dThickness
|
||||
end
|
||||
-- TODO qui sostituire con il valore reale letto dal SetupInfo
|
||||
-- per Fast si dovrà aggiungere la lunghezza del massimo utensile utilizzabile con lama
|
||||
local dHeadDepth = 480
|
||||
local dHeadWidth = 480
|
||||
local ptOpposite = ptMaxElev + Edge.vtN * dHeadWidth
|
||||
local ptCross = ptOpposite + vtHead * dHeadDepth
|
||||
local idHeadRectangle = EgtRectangle3P( idTempGroup, ptMaxElev, ptCross, ptOpposite, GDB_RT.GLOB)
|
||||
-- flat region dal rettangolo
|
||||
local idHeadSurfFr = EgtSurfFlatRegion( idTempGroup, idHeadRectangle)
|
||||
|
||||
-- intersezione tra pezzo e motore (se fallisce si inverte la flat region del motore, probabile normale opposta)
|
||||
local bIntersectSuccess = EgtSurfFrIntersect( idPartSurfFr, idHeadSurfFr)
|
||||
if not bIntersectSuccess then
|
||||
EgtInvertSurf( idHeadSurfFr)
|
||||
bIntersectSuccess = EgtSurfFrIntersect( idPartSurfFr, idHeadSurfFr)
|
||||
end
|
||||
if not bIntersectSuccess then
|
||||
error( 'Check2DBladeCollision : intersect fail')
|
||||
end
|
||||
|
||||
local bCollisionFoundPiece = EgtExistsObj( idPartSurfFr)
|
||||
|
||||
-- intersezione tra grezzo restante e motore, se con il pezzo non c'è collisione
|
||||
local bCollisionFoundRestLength
|
||||
if not bCollisionFoundPiece then
|
||||
bIntersectSuccess = EgtSurfFrIntersect( idRestLengthSurfFr, idHeadSurfFr)
|
||||
if not bIntersectSuccess then
|
||||
EgtInvertSurf( idHeadSurfFr)
|
||||
bIntersectSuccess = EgtSurfFrIntersect( idRestLengthSurfFr, idHeadSurfFr)
|
||||
end
|
||||
if not bIntersectSuccess then
|
||||
error( 'Check2DBladeCollision : intersect fail')
|
||||
end
|
||||
|
||||
bCollisionFoundRestLength = EgtExistsObj( idRestLengthSurfFr)
|
||||
end
|
||||
|
||||
return bCollisionFoundPiece, bCollisionFoundRestLength
|
||||
end
|
||||
|
||||
-------------------------------------------------------------------------------------------------------------
|
||||
-- ritorna se la faccia e il lato sono lavorabili e, se sì, il modo di lavorare (standard/DownUp)
|
||||
-- TODO si dovrà decidere come tagliare anche in base a lavorazione di coda (spostare dopo separazione?) o pezzo corto (il motore non deve ingombrare con il pinzaggio)
|
||||
-- valutare se restituire, se disponibili, entrambe le soluzioni e demandare la decisione alla FaceByBlade
|
||||
function MachiningLib.GetBladeEngagement( Face, Edge, Part, Tool, dDepthToMachine, bCollisionCheckForDownUpOnly)
|
||||
local sBladeEngagement = 'Standard'
|
||||
|
||||
-- la normale della faccia permette di lavorare in modo standard, ma potrebbero esserci altre condizioni che fanno fallire il taglio
|
||||
if not IsFaceZOutOfRange( Face.vtN, Tool) then
|
||||
|
||||
-- TODO verifica collisione carro Z, collisione traversa PF, collisione 'C' Fast... La riduzione percorso cambia questo test?
|
||||
local bCollisionFound, bMoveAfterSplit = Check2DBladeCollision( Edge, Face.vtN, Face.vtN, Part, Tool, dDepthToMachine)
|
||||
if bCollisionCheckForDownUpOnly or not bCollisionFound then
|
||||
|
||||
return true, sBladeEngagement, bMoveAfterSplit
|
||||
end
|
||||
end
|
||||
|
||||
-- faccia non lavorabile in modo standard: si verifica se il DownUp è fattibile
|
||||
-- la normale della faccia non permette il DownUp: non lavorabile in DownUp (se taglio DownUp la faccia è lavorata al contrario, vtN opposta)
|
||||
if IsFaceZOutOfRange( -Face.vtN, Tool) then
|
||||
|
||||
return false
|
||||
end
|
||||
|
||||
-- rischio collisione carro Z: non lavorabile in Downup
|
||||
-- TODO questo test è da spostare sulla macchina, non è universale
|
||||
local bIsToolBelowWorkpiece = Edge.vtN:getZ() < - 0.5
|
||||
local bIsToolAboveWorkpiece = Edge.vtN:getZ() > 0.5
|
||||
|
||||
if Tool.SetupInfo.HeadType.bTop and bIsToolBelowWorkpiece
|
||||
or ( Tool.SetupInfo.HeadType.bBottom and bIsToolAboveWorkpiece) then
|
||||
|
||||
return false
|
||||
end
|
||||
|
||||
-- orientamento faccia / utensile compatibili con DownUp: lavorabile
|
||||
local bCollisionFound, bMoveAfterSplit = Check2DBladeCollision( Edge, Face.vtN, -Face.vtN, Part, Tool, dDepthToMachine)
|
||||
if not bCollisionFound then
|
||||
|
||||
sBladeEngagement = 'DownUp'
|
||||
|
||||
return true, sBladeEngagement, bMoveAfterSplit
|
||||
end
|
||||
|
||||
return false
|
||||
end
|
||||
|
||||
-------------------------------------------------------------------------------------------------------------
|
||||
-- funzione per cercare utensile tipo FRESA con certe caratteristiche
|
||||
-- TODO qui vtToolDirection è in realtà vtN
|
||||
@@ -383,14 +539,14 @@ end
|
||||
|
||||
-------------------------------------------------------------------------------------------------------------
|
||||
-- funzione per cercare utensile tipo LAMA con certe caratteristiche
|
||||
-- TODO da completare
|
||||
-- TODO da rivedere/completare
|
||||
-- TODO il FindBlade dovrà restituire di utilizzare sempre la lama sopra se l'angolo lo permette, ma avendo un'altezza massima (da macchina) oltre cui il DownUp non sarà fattibile (evita collisioni tra asse e pezzo)
|
||||
function MachiningLib.FindBlade( Proc, ToolSearchParameters)
|
||||
local ToolInfo = {}
|
||||
|
||||
-- parametri obbligatori
|
||||
if type( ToolSearchParameters.vtN) ~= 'table' then
|
||||
error( 'FindBlade : missing tool direction')
|
||||
if type( ToolSearchParameters.FaceToMachine) ~= 'table' then
|
||||
error( 'FindBlade : missing face info')
|
||||
end
|
||||
if type( ToolSearchParameters.bAllowTopHead) ~= 'boolean' then
|
||||
error( 'FindBlade : missing top head info')
|
||||
@@ -401,32 +557,52 @@ function MachiningLib.FindBlade( Proc, ToolSearchParameters)
|
||||
if not ToolSearchParameters.bAllowTopHead and not ToolSearchParameters.bAllowBottomHead then
|
||||
error( 'FindBlade : wrong head info')
|
||||
end
|
||||
local FaceToMachine = ToolSearchParameters.FaceToMachine
|
||||
local bAllowTopHead = ToolSearchParameters.bAllowTopHead
|
||||
local bAllowBottomHead = ToolSearchParameters.bAllowBottomHead
|
||||
|
||||
-- parametri opzionali
|
||||
ToolSearchParameters.dElevation = ToolSearchParameters.dElevation or 0
|
||||
ToolSearchParameters.bForceLongcutBlade = ToolSearchParameters.bForceLongcutBlade or false
|
||||
local dElevation = ToolSearchParameters.dElevation or 0
|
||||
local bForceLongcutBlade = ToolSearchParameters.bForceLongcutBlade or false
|
||||
local EdgeToMachine = ToolSearchParameters.EdgeToMachine
|
||||
local Part = ToolSearchParameters.Part
|
||||
local bCollisionCheckForDownUpOnly = ToolSearchParameters.bCollisionCheckForDownUpOnly or false
|
||||
|
||||
local nBestToolIndex
|
||||
local dBestToolResidualDepth = 0
|
||||
local sCurrentBladeEngagement
|
||||
local sBestBladeEngagement
|
||||
local bCurrentMoveAfterSplit
|
||||
local bBestMoveAfterSplit
|
||||
for i = 1, #TOOLS do
|
||||
local bIsToolCompatible = false
|
||||
|
||||
if TOOLS[i].sFamily == 'SAWBLADE' then
|
||||
if ToolSearchParameters.bAllowTopHead and not ToolSearchParameters.bAllowBottomHead then
|
||||
if bAllowTopHead and not bAllowBottomHead then
|
||||
bIsToolCompatible = TOOLS[i].SetupInfo.HeadType.bTop
|
||||
elseif ToolSearchParameters.bAllowBottomHead and not ToolSearchParameters.bAllowTopHead then
|
||||
elseif bAllowBottomHead and not bAllowTopHead then
|
||||
bIsToolCompatible = TOOLS[i].SetupInfo.HeadType.bBottom
|
||||
else
|
||||
bIsToolCompatible = true
|
||||
end
|
||||
end
|
||||
|
||||
-- check angolo limite lama
|
||||
if TOOLS[i].SetupInfo.HeadType.bTop and ToolSearchParameters.vtN:getZ() < TOOLS[i].SetupInfo.GetMinNz( ToolSearchParameters.vtN, TOOLS[i]) - GEO.EPS_ZERO then
|
||||
bIsToolCompatible = false
|
||||
end
|
||||
if TOOLS[i].SetupInfo.HeadType.bBottom and ToolSearchParameters.vtN:getZ() > TOOLS[i].SetupInfo.GetMaxNz( ToolSearchParameters.vtN, TOOLS[i]) + GEO.EPS_ZERO then
|
||||
bIsToolCompatible = false
|
||||
-- se dati sufficienti, si determina se con questo utensile il taglio è fattibile e il modo di lavorare della lama
|
||||
if bIsToolCompatible then
|
||||
if FaceToMachine and EdgeToMachine and Part and dElevation then
|
||||
local bIsBladeOk = false
|
||||
bIsBladeOk, sCurrentBladeEngagement, bCurrentMoveAfterSplit = MachiningLib.GetBladeEngagement( FaceToMachine, EdgeToMachine, Part, TOOLS[i], dElevation, bCollisionCheckForDownUpOnly)
|
||||
-- orientamento non raggiungibile
|
||||
if not bIsBladeOk then
|
||||
bIsToolCompatible = false
|
||||
end
|
||||
|
||||
-- se si ha solo la faccia si può verificare se questa è orientata correttamente
|
||||
elseif FaceToMachine then
|
||||
if IsFaceZOutOfRange( FaceToMachine.vtN, TOOLS[i]) then
|
||||
bIsToolCompatible = false
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
-- se c'è una lista di utensili disponibili, si verifica che l'utensile attuale sia tra quelli
|
||||
@@ -436,15 +612,19 @@ function MachiningLib.FindBlade( Proc, ToolSearchParameters)
|
||||
|
||||
if bIsToolCompatible then
|
||||
-- TODO gestire accorciamento massimo materiale per inclinazione
|
||||
local dCurrentResidualDepth = ToolSearchParameters.dElevation - TOOLS[i].dMaxDepth
|
||||
local dCurrentResidualDepth = dElevation - TOOLS[i].dMaxDepth
|
||||
if not nBestToolIndex or ( dBestToolResidualDepth > 0 and dCurrentResidualDepth <= 10 * GEO.EPS_SMALL) then
|
||||
nBestToolIndex = i
|
||||
dBestToolResidualDepth = dCurrentResidualDepth
|
||||
sBestBladeEngagement = sCurrentBladeEngagement
|
||||
bBestMoveAfterSplit = bCurrentMoveAfterSplit
|
||||
else
|
||||
-- prediligo utensile per tagli lunghi, se richiesto
|
||||
if ToolSearchParameters.bForceLongcutBlade and not TOOLS[nBestToolIndex].bIsUsedForLongCut and TOOLS[i].bIsUsedForLongCut then
|
||||
-- prediligo utensile per tagli lungo vena, se richiesto
|
||||
if bForceLongcutBlade and not TOOLS[nBestToolIndex].bIsUsedForLongCut and TOOLS[i].bIsUsedForLongCut then
|
||||
nBestToolIndex = i
|
||||
dBestToolResidualDepth = dCurrentResidualDepth
|
||||
sBestBladeEngagement = sCurrentBladeEngagement
|
||||
bBestMoveAfterSplit = bCurrentMoveAfterSplit
|
||||
else
|
||||
-- entrambi completi
|
||||
if dBestToolResidualDepth <= 10 * GEO.EPS_SMALL and dCurrentResidualDepth <= 10 * GEO.EPS_SMALL then
|
||||
@@ -455,11 +635,15 @@ function MachiningLib.FindBlade( Proc, ToolSearchParameters)
|
||||
GetIndexToolInAvailableToolList( ToolSearchParameters.AvailableToolList, TOOLS[nBestToolIndex].sName) then
|
||||
nBestToolIndex = i
|
||||
dBestToolResidualDepth = dCurrentResidualDepth
|
||||
sBestBladeEngagement = sCurrentBladeEngagement
|
||||
bBestMoveAfterSplit = bCurrentMoveAfterSplit
|
||||
end
|
||||
-- si sceglie quello con le performance migliori
|
||||
elseif TOOLS[i].dPerformanceIndex > TOOLS[nBestToolIndex].dPerformanceIndex + 10 * GEO.EPS_SMALL then
|
||||
nBestToolIndex = i
|
||||
dBestToolResidualDepth = dCurrentResidualDepth
|
||||
sBestBladeEngagement = sCurrentBladeEngagement
|
||||
bBestMoveAfterSplit = bCurrentMoveAfterSplit
|
||||
end
|
||||
-- entrambi incompleti
|
||||
elseif dBestToolResidualDepth > 10 * GEO.EPS_SMALL and dCurrentResidualDepth > 10 * GEO.EPS_SMALL then
|
||||
@@ -467,6 +651,8 @@ function MachiningLib.FindBlade( Proc, ToolSearchParameters)
|
||||
if dCurrentResidualDepth > dBestToolResidualDepth then
|
||||
nBestToolIndex = i
|
||||
dBestToolResidualDepth = dCurrentResidualDepth
|
||||
sBestBladeEngagement = sCurrentBladeEngagement
|
||||
bBestMoveAfterSplit = bCurrentMoveAfterSplit
|
||||
end
|
||||
end
|
||||
end
|
||||
@@ -476,6 +662,8 @@ function MachiningLib.FindBlade( Proc, ToolSearchParameters)
|
||||
|
||||
ToolInfo.nToolIndex = nBestToolIndex
|
||||
ToolInfo.dResidualDepth = dBestToolResidualDepth
|
||||
ToolInfo.sBladeEngagement = sBestBladeEngagement
|
||||
ToolInfo.bMoveAfterSplit = bBestMoveAfterSplit
|
||||
|
||||
return ToolInfo
|
||||
end
|
||||
@@ -1284,9 +1472,9 @@ function MachiningLib.GetTimeToMachineAllStepsWithLeadInOut( Machining, Part)
|
||||
local ProcTm = FeatureLib.GetProcFromTrimesh( Machining.Geometry[1][1], Part)
|
||||
local dDepthToMachine = min( ProcTm.Faces[Machining.Geometry[1][2] + 1].dElevation, ( Machining.dMaxElev or ProcTm.Faces[Machining.Geometry[1][2] + 1].dElevation)) - ( max( 0, Machining.dResidualDepth or 0))
|
||||
local nSteps = max( ceil( ( dDepthToMachine - 50 * GEO.EPS_SMALL) / TOOLS[Machining.nToolIndex].dStep), 1)
|
||||
local nAddGroupId = BeamLib.GetAddGroup( Part.id)
|
||||
local idTempGroup = BeamLib.GetTempGroup()
|
||||
-- TODO in futuro creare flatregion (se ci fossero isole il calcolo del percorso non sarebbe corretto)
|
||||
local idFaceContour = EgtExtractSurfTmFacetLoops( ProcTm.id, Machining.Geometry[1][2], nAddGroupId)
|
||||
local idFaceContour = EgtExtractSurfTmFacetLoops( ProcTm.id, Machining.Geometry[1][2], idTempGroup)
|
||||
-- si settano i lati aperti della curva derivata dalla superficie
|
||||
for i = 1, #ProcTm.Faces[Machining.Geometry[1][2] + 1].Edges do
|
||||
if ProcTm.Faces[Machining.Geometry[1][2] + 1].Edges[i].bIsOpen then
|
||||
@@ -1294,7 +1482,7 @@ function MachiningLib.GetTimeToMachineAllStepsWithLeadInOut( Machining, Part)
|
||||
end
|
||||
end
|
||||
-- dal momento che la funzione EgtPocketing non considera il grezzo, nei casi ottimizzati si deve correggere l'offset
|
||||
local idTestCurve = EgtCopyGlob( idFaceContour, nAddGroupId )
|
||||
local idTestCurve = EgtCopyGlob( idFaceContour, idTempGroup )
|
||||
local bIsOptimizedPocketing = ( TOOLS[Machining.nToolIndex].dDiameter > TOOLS[Machining.nToolIndex].dSideStep - 10 * GEO.EPS_SMALL)
|
||||
and EgtOffsetCurve( idTestCurve, -TOOLS[Machining.nToolIndex].dDiameter / 2 - 10 * GEO.EPS_SMALL)
|
||||
if not bIsOptimizedPocketing then
|
||||
@@ -1310,7 +1498,7 @@ function MachiningLib.GetTimeToMachineAllStepsWithLeadInOut( Machining, Part)
|
||||
end
|
||||
end
|
||||
-- calcolo percorso di svuotatura replicando il calcolo che fa la svuotatura
|
||||
local idPocketingPath = EgtPocketing( idFaceContour, TOOLS[Machining.nToolIndex].dDiameter / 2, TOOLS[Machining.nToolIndex].dSideStep, 0, Machining.nSubType, true, nAddGroupId)
|
||||
local idPocketingPath = EgtPocketing( idFaceContour, TOOLS[Machining.nToolIndex].dDiameter / 2, TOOLS[Machining.nToolIndex].dSideStep, 0, Machining.nSubType, true, idTempGroup)
|
||||
local dPocketingPathLength = EgtCurveLength( idPocketingPath)
|
||||
-- calcolo lunghezze e tempi totali
|
||||
if dPocketingPathLength then
|
||||
@@ -1322,10 +1510,6 @@ function MachiningLib.GetTimeToMachineAllStepsWithLeadInOut( Machining, Part)
|
||||
dLengthToMachineAllStepsWithLeadInOut = 99999 * nSteps
|
||||
dTimeToMachineTotal = dLengthToMachineAllStepsWithLeadInOut / dToolFeed
|
||||
end
|
||||
-- le geometrie create si settano da cancellare
|
||||
EgtSetLevel( idFaceContour, GDB_LV.TEMP)
|
||||
EgtSetLevel( idPocketingPath, GDB_LV.TEMP)
|
||||
EgtSetLevel( idTestCurve, GDB_LV.TEMP)
|
||||
else
|
||||
error( 'GetTimeToMachineAllStepsWithLeadInOut : unknown machining type')
|
||||
end
|
||||
|
||||
+1
-1
@@ -320,7 +320,7 @@ local function MyProcessFeatures()
|
||||
sMsg = string.gsub( sMsg or '', '\r', ' ', 10)
|
||||
-- trovata almeno una strategia e feature lavorata completamente
|
||||
if RESULT[i].sType == 'Feature' and RESULT[i].ChosenStrategy.sStatus == 'Completed' then
|
||||
-- nulla da segnalare
|
||||
sOutput = sOutput .. string.format( '[%d,%d] %s\n', RESULT[i].idCut, RESULT[i].idTask, sMsg or '')
|
||||
|
||||
-- trovata almeno una strategia ma nessuna applicabile oppure non trovata alcuna strategia
|
||||
elseif RESULT[i].sType == 'Feature'
|
||||
|
||||
@@ -89,8 +89,7 @@ function HEADCUT.Make( bAddMachining, Proc, Part, CustomParameters)
|
||||
if not bExecutePrecutOnly then
|
||||
local OptionalParameters = {}
|
||||
-- si parte dal box della feature e si aggiunge il punto estremo del grezzo
|
||||
-- ATTENZIONE : Proc.b3Box viene modificata dato che il tipo Box è come se fosse una tabella, ma da qui passa solo 1 volta per pezzo quindi non dovrebbero esserci problemi
|
||||
local b3BoxDicing = Proc.b3Box
|
||||
local b3BoxDicing = BBox3d( Proc.b3Box)
|
||||
b3BoxDicing:Add( Part.b3Raw:getMax())
|
||||
b3BoxDicing:expand( 1000 * GEO.EPS_SMALL)
|
||||
OptionalParameters.b3BoxDicing = b3BoxDicing
|
||||
|
||||
@@ -428,7 +428,12 @@ end
|
||||
local function GetSplitSurfaces( Proc, Part, bAddMachining)
|
||||
local vAddId = {}
|
||||
local vAddIdTunnel = {}
|
||||
local nAddGrpId = BeamLib.GetAddGroup( Part.id)
|
||||
local idAddGroup
|
||||
if bAddMachining then
|
||||
idAddGroup = BeamLib.GetAddGroup( Part.id)
|
||||
else
|
||||
idAddGroup = BeamLib.GetTempGroup()
|
||||
end
|
||||
local nOriginalTmIdTunnel = GDB_ID.NULL
|
||||
if Proc.MainFaces.TunnelAddedFaces then
|
||||
nOriginalTmIdTunnel = Proc.MainFaces.TunnelAddedFaces.MiddleFaceTm.id
|
||||
@@ -438,18 +443,14 @@ local function GetSplitSurfaces( Proc, Part, bAddMachining)
|
||||
local FeatureSplittingPoints = FeatureLib.GetFeatureSplittingPoints( Proc, Part)
|
||||
|
||||
if #FeatureSplittingPoints == 0 then
|
||||
local nAddId = EgtCopyGlob( Proc.id, nAddGrpId) or GDB_ID.NULL
|
||||
local nAddIdTunnel = EgtCopyGlob( nOriginalTmIdTunnel, nAddGrpId) or GDB_ID.NULL
|
||||
if not bAddMachining then
|
||||
EgtSetLevel( nAddId, GDB_LV.TEMP)
|
||||
EgtSetLevel( nAddIdTunnel, GDB_LV.TEMP)
|
||||
end
|
||||
local nAddId = EgtCopyGlob( Proc.id, idAddGroup) or GDB_ID.NULL
|
||||
local nAddIdTunnel = EgtCopyGlob( nOriginalTmIdTunnel, idAddGroup) or GDB_ID.NULL
|
||||
table.insert( vAddId, nAddId)
|
||||
table.insert( vAddIdTunnel, nAddIdTunnel)
|
||||
else
|
||||
for i = 1, #FeatureSplittingPoints do
|
||||
local nAddId = EgtCopyGlob( Proc.id, nAddGrpId) or GDB_ID.NULL
|
||||
local nAddIdTunnel = EgtCopyGlob( nOriginalTmIdTunnel, nAddGrpId) or GDB_ID.NULL
|
||||
local nAddId = EgtCopyGlob( Proc.id, idAddGroup) or GDB_ID.NULL
|
||||
local nAddIdTunnel = EgtCopyGlob( nOriginalTmIdTunnel, idAddGroup) or GDB_ID.NULL
|
||||
if i == 1 then
|
||||
-- prima superficie, va tagliata solo a sinistra
|
||||
local ptSplit = FeatureSplittingPoints[i] + Vector3d( -BeamData.MILL_OVERLAP / 2, 0, 0)
|
||||
@@ -465,23 +466,15 @@ local function GetSplitSurfaces( Proc, Part, bAddMachining)
|
||||
EgtCutSurfTmPlane( nAddId, ptSplit, X_AX(), true, GDB_RT.GLOB)
|
||||
EgtCutSurfTmPlane( nAddIdTunnel, ptSplit, X_AX(), true, GDB_RT.GLOB)
|
||||
end
|
||||
if not bAddMachining then
|
||||
EgtSetLevel( nAddId, GDB_LV.TEMP)
|
||||
EgtSetLevel( nAddIdTunnel, GDB_LV.TEMP)
|
||||
end
|
||||
table.insert( vAddId, nAddId)
|
||||
table.insert( vAddIdTunnel, nAddIdTunnel)
|
||||
end
|
||||
-- taglio ultima superficie, va tagliata solo a destra
|
||||
local nAddId = EgtCopyGlob( Proc.id, nAddGrpId) or GDB_ID.NULL
|
||||
local nAddIdTunnel = EgtCopyGlob( nOriginalTmIdTunnel, nAddGrpId) or GDB_ID.NULL
|
||||
local nAddId = EgtCopyGlob( Proc.id, idAddGroup) or GDB_ID.NULL
|
||||
local nAddIdTunnel = EgtCopyGlob( nOriginalTmIdTunnel, idAddGroup) or GDB_ID.NULL
|
||||
local ptSplit = FeatureSplittingPoints[#FeatureSplittingPoints] + Vector3d( BeamData.MILL_OVERLAP / 2, 0, 0)
|
||||
EgtCutSurfTmPlane( nAddId, ptSplit, X_AX(), true, GDB_RT.GLOB)
|
||||
EgtCutSurfTmPlane( nAddIdTunnel, ptSplit, X_AX(), true, GDB_RT.GLOB)
|
||||
if not bAddMachining then
|
||||
EgtSetLevel( nAddId, GDB_LV.TEMP)
|
||||
EgtSetLevel( nAddIdTunnel, GDB_LV.TEMP)
|
||||
end
|
||||
table.insert( vAddId, nAddId)
|
||||
table.insert( vAddIdTunnel, nAddIdTunnel)
|
||||
end
|
||||
|
||||
@@ -236,6 +236,7 @@ function STR0003.Make( bAddMachining, Proc, Part, CustomParameters)
|
||||
local BottomEdge = LongFace.MainEdges.BottomEdge
|
||||
|
||||
-- TODO funzione separata
|
||||
-- TODO è meglio cercare la lama qui e passarla alla FACEBYBLADE, la scelta è più precisa
|
||||
-- lama - calcolo lavorazioni
|
||||
local Cutting = {}
|
||||
-- parametri comuni a tutte le lavorazioni cutting
|
||||
@@ -243,8 +244,7 @@ function STR0003.Make( bAddMachining, Proc, Part, CustomParameters)
|
||||
bForceLongcutBlade = Strategy.Parameters.bForceLongcutBlade,
|
||||
dExtendAfterTail = dExtendAfterTail,
|
||||
dPocketHeight = dPocketHeight,
|
||||
bIsSplitFeature = bIsSplitFeature,
|
||||
dMinNzDownUp = 0
|
||||
bIsSplitFeature = bIsSplitFeature
|
||||
}
|
||||
|
||||
-- primo lato del tunnel o lato di fondo
|
||||
|
||||
@@ -36,7 +36,7 @@ local function IsTwoFacesCommonEdgeTooLong( Proc, Part)
|
||||
end
|
||||
|
||||
-- se due facce, cubetti troppo lunghi in X non si possono fare
|
||||
local ptEdge1, _, ptEdge2 = EgtSurfTmFacetOppositeSide( Proc.id, Proc.Faces[1].id, -Proc.Faces[1].Edges[nCommonEdge].vtN, GDB_ID.ROOT)
|
||||
local ptEdge1, ptEdge2 = Proc.Faces[1].Edges[nCommonEdge].ptStart, Proc.Faces[1].Edges[nCommonEdge].ptEnd
|
||||
local b3BoxEdge = BBox3d( ptEdge1, ptEdge2)
|
||||
local dEdgeLengthOnX = b3BoxEdge:getDimX()
|
||||
if FeatureLib.IsMachiningLong( dEdgeLengthOnX, Part) then
|
||||
@@ -111,13 +111,14 @@ function STR0005.Make( bAddMachining, Proc, Part, CustomParameters)
|
||||
or bKeepWasteAttached then
|
||||
|
||||
local BladeKeepWasteResult
|
||||
local OptionalParameters = { dExtendAfterTail = dExtendAfterTail, dStripWidth = Strategy.Parameters.dStripWidth}
|
||||
local OptionalParameters = { dExtendAfterTail = dExtendAfterTail, dStripWidth = Strategy.Parameters.dStripWidth, bForced = bKeepWasteAttached}
|
||||
AuxiliaryData.bIgnoreNotClampableLength = true
|
||||
Blade.Result, BladeKeepWasteResult = BladeKeepWaste.Make( Proc, Part, OptionalParameters)
|
||||
dTimeToMachine = BladeKeepWasteResult.dTimeToMachine
|
||||
dMRRBlade = BladeKeepWasteResult.dMRR
|
||||
dCompletionPercentage = BladeKeepWasteResult.dCompletionPercentage
|
||||
dQuality = BladeKeepWasteResult.dQuality
|
||||
Strategy.Result.sInfo = BladeKeepWasteResult.sInfo or ''
|
||||
end
|
||||
|
||||
-- lavorazione a cubetti / taglio singolo
|
||||
|
||||
@@ -108,15 +108,17 @@ local function GetRoughStrategy( Proc, Part, bSaveAddedGeometries)
|
||||
local nMidFacet = Proc.nFct // 2 -- faccia a metà circa
|
||||
local vtN = EgtSurfTmFacetNormVersor( Proc.id, nMidFacet, GDB_ID.ROOT)
|
||||
|
||||
local nAddGroupId = BeamLib.GetAddGroup( Part.id)
|
||||
local idAddGroup
|
||||
if bSaveAddedGeometries then
|
||||
idAddGroup = BeamLib.GetAddGroup( Part.id)
|
||||
else
|
||||
idAddGroup = BeamLib.GetTempGroup()
|
||||
end
|
||||
-- aggiungo piano di sgrossatura e lo lavoro
|
||||
local ptStart, vtNP = GetSawCutData( Proc, Proc.idAddAuxGeom, vtNF, vtN)
|
||||
local AddId = EgtSurfTmPlaneInBBox( nAddGroupId, ptStart, vtNP, Part.b3Part, GDB_RT.GLOB)
|
||||
local AddId = EgtSurfTmPlaneInBBox( idAddGroup, ptStart, vtNP, Part.b3Part, GDB_RT.GLOB)
|
||||
-- se la faccia è stata creata
|
||||
if AddId then
|
||||
if not bSaveAddedGeometries then
|
||||
EgtSetLevel( AddId, GDB_LV.TEMP)
|
||||
end
|
||||
|
||||
-- creo piano di taglio sulla testa del tenone
|
||||
local OptionalParameters = { dMaxWasteVolume = Strategy.Parameters.dMaxWasteVolume,
|
||||
|
||||
@@ -11,6 +11,7 @@ require( 'EgtBase')
|
||||
local FeatureLib = require( 'FeatureLib')
|
||||
local FaceData = require( 'FaceData')
|
||||
local MachiningLib = require( 'MachiningLib')
|
||||
local BeamLib = require('BeamLib')
|
||||
-- strategie di base
|
||||
local FaceByBlade = require('FACEBYBLADE')
|
||||
local FaceByMill = require('FACEBYMILL')
|
||||
@@ -119,8 +120,8 @@ end
|
||||
|
||||
function BLADEKEEPWASTE.Make( Proc, Part, OptionalParameters)
|
||||
-- TODO verificare funzionamento con lama da sotto
|
||||
-- TODO scelta utensile è corretto lasciarla a FaceByBlade?
|
||||
-- attenzione perchè se l'inclinazione della faccia la fa finire oltre lo spigolo questo riduce il massimo (come calcolare????)
|
||||
-- il FindBlade dovrà restituire di utilizzare sempre la lama sopra se l'angolo lo permette, ma avendo un'altezza massima (da macchina) oltre cui il DownUp non sarà fattibile (evita collisioni tra asse e pezzo)
|
||||
|
||||
local Result = {}
|
||||
local Machinings = {}
|
||||
@@ -171,6 +172,8 @@ function BLADEKEEPWASTE.Make( Proc, Part, OptionalParameters)
|
||||
bFinishWithMill = OptionalParameters.bFinishWithMill
|
||||
end
|
||||
local dMillingOffsetFromSide = OptionalParameters.dMillingOffsetFromSide or 1
|
||||
local dStripWidth = OptionalParameters.dStripWidth or 5
|
||||
local bForced = OptionalParameters.bForced or false
|
||||
|
||||
-- volume della feature
|
||||
local dFeatureVolume = FeatureLib.GetFeatureVolume( Proc, Part)
|
||||
@@ -217,19 +220,41 @@ function BLADEKEEPWASTE.Make( Proc, Part, OptionalParameters)
|
||||
end
|
||||
|
||||
-- taglio con codolo faccia di fondo
|
||||
local dDepthToMachine = BottomEdgeToMachine.dElevation / 2 - OptionalParameters.dStripWidth / 2
|
||||
local OptionalParametersFaceByBlade = { dDepthToMachine = dDepthToMachine, bIsSplitFeature = bIsSplitFeature, dExtendAfterTail = dExtendAfterTail, nToolIndex = nToolIndex}
|
||||
local dDepthToMachine = BottomEdgeToMachine.dElevation / 2 - dStripWidth / 2
|
||||
local OptionalParametersFaceByBlade1 = { dDepthToMachine = dDepthToMachine, bIsSplitFeature = bIsSplitFeature, dExtendAfterTail = dExtendAfterTail, nToolIndex = nToolIndex}
|
||||
-- primo lato
|
||||
Cutting1 = FaceByBlade.Make( Proc, Part, BottomFace, BottomEdgeToMachine, OptionalParametersFaceByBlade)
|
||||
Cutting1 = FaceByBlade.Make( Proc, Part, BottomFace, BottomEdgeToMachine, OptionalParametersFaceByBlade1)
|
||||
Cutting1.nInternalSortingPriority = 3
|
||||
Cutting1.dResultWeight = 0.3
|
||||
table.insert( CalculatedMachinings, Cutting1)
|
||||
|
||||
-- secondo lato
|
||||
OptionalParametersFaceByBlade.OppositeToolDirectionMode = 'Enabled'
|
||||
Cutting2 = FaceByBlade.Make( Proc, Part, BottomFace, BottomEdgeToMachine, OptionalParametersFaceByBlade)
|
||||
local OptionalParametersFaceByBlade2 = BeamLib.TableCopyDeep( OptionalParametersFaceByBlade1)
|
||||
OptionalParametersFaceByBlade2.OppositeToolDirectionMode = 'Enabled'
|
||||
Cutting2 = FaceByBlade.Make( Proc, Part, BottomFace, BottomEdgeToMachine, OptionalParametersFaceByBlade2)
|
||||
Cutting2.nInternalSortingPriority = 3
|
||||
Cutting2.dResultWeight = 0.3
|
||||
table.insert( CalculatedMachinings, Cutting2)
|
||||
|
||||
-- se uno dei due lati non è riuscito, si estende il più possibile il lato rimasto
|
||||
if not Cutting1.bIsApplicable and Cutting2.bIsApplicable then
|
||||
|
||||
dDepthToMachine = min( TOOLS[Cutting2.nToolIndex].dMaxMaterial, BottomEdgeToMachine.dElevation - dStripWidth)
|
||||
OptionalParametersFaceByBlade2.dDepthToMachine = dDepthToMachine
|
||||
|
||||
Cutting2 = FaceByBlade.Make( Proc, Part, BottomFace, BottomEdgeToMachine, OptionalParametersFaceByBlade2)
|
||||
table.insert( CalculatedMachinings, Cutting2)
|
||||
|
||||
elseif not Cutting2.bIsApplicable and Cutting1.bIsApplicable then
|
||||
|
||||
dDepthToMachine = min( TOOLS[Cutting1.nToolIndex].dMaxMaterial, BottomEdgeToMachine.dElevation - dStripWidth)
|
||||
OptionalParametersFaceByBlade1.dDepthToMachine = dDepthToMachine
|
||||
|
||||
Cutting1 = FaceByBlade.Make( Proc, Part, BottomFace, BottomEdgeToMachine, OptionalParametersFaceByBlade1)
|
||||
table.insert( CalculatedMachinings, Cutting1)
|
||||
|
||||
else
|
||||
table.insert( CalculatedMachinings, Cutting1)
|
||||
table.insert( CalculatedMachinings, Cutting2)
|
||||
end
|
||||
|
||||
-- fresatura eventuali facce di chiusura
|
||||
if bFinishWithMill then
|
||||
@@ -253,8 +278,9 @@ function BLADEKEEPWASTE.Make( Proc, Part, OptionalParameters)
|
||||
end
|
||||
end
|
||||
|
||||
-- calcolo completamento, serve la lista di lavorazioni che comprende le non applicabili
|
||||
Result.dCompletionPercentage = GetStrategyCompletionPercentage( CalculatedMachinings)
|
||||
-- calcolo completamento (non applicabili devono essere incluse)
|
||||
-- se codolo non forzato si ritorna completa solo al 94% (completion index 4)
|
||||
Result.dCompletionPercentage = bForced and GetStrategyCompletionPercentage( CalculatedMachinings) or 94
|
||||
Result.dCompletionIndex = FeatureLib.GetFeatureCompletionIndex( Result.dCompletionPercentage)
|
||||
|
||||
-- aggiunta eventuali lavorazioni splittate
|
||||
@@ -272,6 +298,9 @@ function BLADEKEEPWASTE.Make( Proc, Part, OptionalParameters)
|
||||
Result.dMRR = ( dFeatureVolume / Result.dTimeToMachine) / pow( 10, 6)
|
||||
if Result.dCompletionPercentage > 100 - 10 * GEO.EPS_SMALL then
|
||||
Result.sStatus = 'Completed'
|
||||
if bForced then
|
||||
Result.sInfo = 'Waste attached. Remove manually.'
|
||||
end
|
||||
else
|
||||
Result.sStatus = 'Not-Completed'
|
||||
end
|
||||
|
||||
+185
-171
@@ -204,9 +204,14 @@ local function CompareEdgesNoPreference( EdgeA, EdgeB)
|
||||
end
|
||||
|
||||
|
||||
local function GetEdgeToMachine( Edges, vtNFace, sBladeType, bAllowFastCuts)
|
||||
local function GetEdgeToMachine( Edges, sBladeType, OptionalParameters)
|
||||
local EdgeToMachine = {}
|
||||
|
||||
-- parametri opzionali
|
||||
OptionalParameters = OptionalParameters or {}
|
||||
local bAllowFastCuts = OptionalParameters.bAllowFastCuts or false
|
||||
local nIndex = OptionalParameters.nIndex or 1
|
||||
|
||||
local EdgesSorted = {}
|
||||
for i = 1, #Edges do
|
||||
table.insert( EdgesSorted, Edges[i])
|
||||
@@ -218,31 +223,23 @@ local function GetEdgeToMachine( Edges, vtNFace, sBladeType, bAllowFastCuts)
|
||||
else
|
||||
table.sort( EdgesSorted, CompareEdgesTopHead)
|
||||
end
|
||||
EdgeToMachine = EdgesSorted[1]
|
||||
EdgeToMachine = EdgesSorted[nIndex]
|
||||
elseif sBladeType == 'Bottom' then
|
||||
table.sort( EdgesSorted, CompareEdgesBottomHead)
|
||||
EdgeToMachine = EdgesSorted[1]
|
||||
elseif sBladeType == 'TopDownUp' then
|
||||
local vtEdgeDirection
|
||||
if vtNFace:getY() > -0.02 then
|
||||
vtEdgeDirection = -Y_AX()
|
||||
else
|
||||
vtEdgeDirection = Y_AX()
|
||||
end
|
||||
EdgeToMachine = BeamLib.FindEdgeBestOrientedAsDirection( Edges, vtEdgeDirection)
|
||||
EdgeToMachine = EdgesSorted[nIndex]
|
||||
elseif sBladeType == 'TopGuillotine' then
|
||||
table.sort( EdgesSorted, CompareEdgesTopHeadGuillotine)
|
||||
EdgeToMachine = EdgesSorted[1]
|
||||
EdgeToMachine = EdgesSorted[nIndex]
|
||||
elseif sBladeType == 'HorizontalBottom' then
|
||||
table.sort( EdgesSorted, CompareEdgesHorizontalBottom)
|
||||
EdgeToMachine = EdgesSorted[1]
|
||||
EdgeToMachine = EdgesSorted[nIndex]
|
||||
elseif sBladeType == 'Vertical' then
|
||||
table.sort( EdgesSorted, CompareEdgesVertical)
|
||||
EdgeToMachine = EdgesSorted[1]
|
||||
EdgeToMachine = EdgesSorted[nIndex]
|
||||
-- TODO non testato; non si dovrebbe mai entrare in questo caso
|
||||
else
|
||||
table.sort( EdgesSorted, CompareEdgesNoPreference)
|
||||
EdgeToMachine = EdgesSorted[1]
|
||||
EdgeToMachine = EdgesSorted[nIndex]
|
||||
end
|
||||
|
||||
return EdgeToMachine
|
||||
@@ -262,9 +259,10 @@ local function GetBestBlade( Proc, Part, Face, OptionalParameters)
|
||||
local dMinNzTopBladeIfEqual = OptionalParameters.dMinNzTopBlade or sin(-5)
|
||||
local dMaxNyTopBlade = OptionalParameters.dMaxNyTopBlade or sin(1)
|
||||
local dShortPartLength = OptionalParameters.dShortPartLength or BeamData.LEN_SHORT_PART
|
||||
local dElevationTop = OptionalParameters.dElevationTop
|
||||
local dElevationBottom = OptionalParameters.dElevationBottom
|
||||
local dElevationTopDownUp = OptionalParameters.dElevationTopDownUp or 0
|
||||
local EdgeToMachineTop = OptionalParameters.EdgeToMachineTop
|
||||
local EdgeToMachineBottom = OptionalParameters.EdgeToMachineBottom
|
||||
local dElevationTop = EdgeToMachineTop and EdgeToMachineTop.dElevation + BeamData.CUT_EXTRA or nil
|
||||
local dElevationBottom = EdgeToMachineBottom and EdgeToMachineBottom.dElevation + BeamData.CUT_EXTRA or nil
|
||||
|
||||
-- se ho già l'utensile, devo solo discriminare se è lama sopra o sotto e verificare se ci arriva
|
||||
if OptionalParameters.nToolIndex then
|
||||
@@ -282,20 +280,24 @@ local function GetBestBlade( Proc, Part, Face, OptionalParameters)
|
||||
local ToolInfo
|
||||
-- ricerca lama testa sopra
|
||||
ToolInfo = MachiningLib.FindBlade( Proc, {
|
||||
vtN = Face.vtN,
|
||||
bAllowTopHead = true,
|
||||
bAllowBottomHead = false,
|
||||
dElevation = dElevationTop
|
||||
dElevation = dElevationTop,
|
||||
FaceToMachine = Face,
|
||||
EdgeToMachine = EdgeToMachineTop,
|
||||
Part = Part
|
||||
})
|
||||
if ToolInfo.dResidualDepth < 10 * GEO.EPS_SMALL then
|
||||
nToolIndexTop = ToolInfo.nToolIndex
|
||||
end
|
||||
-- ricerca lama testa sotto
|
||||
ToolInfo = MachiningLib.FindBlade( Proc, {
|
||||
vtN = Face.vtN,
|
||||
bAllowTopHead = false,
|
||||
bAllowBottomHead = true,
|
||||
dElevation = dElevationBottom
|
||||
dElevation = dElevationBottom,
|
||||
FaceToMachine = Face,
|
||||
EdgeToMachine = EdgeToMachineBottom,
|
||||
Part = Part
|
||||
})
|
||||
if ToolInfo.dResidualDepth < 10 * GEO.EPS_SMALL then
|
||||
nToolIndexBottom = ToolInfo.nToolIndex
|
||||
@@ -337,19 +339,8 @@ local function GetBestBlade( Proc, Part, Face, OptionalParameters)
|
||||
-- assegnazione tipo lama
|
||||
if nChosenToolIndex == nToolIndexBottom then
|
||||
sChosenBladeType = 'Bottom'
|
||||
-- se lama sopra va verificato se va usata in DownUp
|
||||
elseif nChosenToolIndex == nToolIndexTop then
|
||||
local dMinNzDownUp = TOOLS[nToolIndexTop].SetupInfo.GetMinNzDownUp( Part.b3Raw, Face.vtN, nil, TOOLS[nToolIndexTop])
|
||||
local dCurrentResidualDepth = dElevationTopDownUp - TOOLS[nToolIndexTop].dMaxDepth
|
||||
if Face.vtN:getZ() < dMinNzDownUp then
|
||||
if ( dCurrentResidualDepth > 10 * GEO.EPS_SMALL) then
|
||||
-- TODO serve messaggio per motivare il non applicabile??
|
||||
nChosenToolIndex = nil
|
||||
end
|
||||
sChosenBladeType = 'TopDownUp'
|
||||
else
|
||||
sChosenBladeType = 'Top'
|
||||
end
|
||||
sChosenBladeType = 'Top'
|
||||
end
|
||||
|
||||
-- se non trovata alcuna lama ritorna nil
|
||||
@@ -357,13 +348,8 @@ local function GetBestBlade( Proc, Part, Face, OptionalParameters)
|
||||
end
|
||||
|
||||
|
||||
local function SetDiceFaceInfo( Proc, idDiceFace, bSaveAddedGeometries)
|
||||
EgtSetName( idDiceFace, 'Face' .. tostring( Proc.idFeature) .. '_Dice')
|
||||
-- TODO la scrittura del TaskId probabilmente non serve (è fatta nell'AddOperations)
|
||||
EgtSetInfo( idDiceFace, 'TASKID', Proc.idTask)
|
||||
if not bSaveAddedGeometries then
|
||||
EgtSetLevel( idDiceFace, GDB_LV.TEMP)
|
||||
end
|
||||
local function SetDiceFaceInfo( Proc, idDiceFace)
|
||||
EgtSetName( idDiceFace, 'Face' .. tostring( Proc.idFeature or 'Add') .. '_Dice')
|
||||
end
|
||||
|
||||
|
||||
@@ -376,52 +362,71 @@ local function GetSingleCutStrategy( Proc, Part, OptionalParameters)
|
||||
local bAllowFastCuts = OptionalParameters.bAllowFastCuts or false
|
||||
local FaceToMachine = Proc.Faces[OptionalParameters.nFaceToMachineIndex or 1]
|
||||
-- lati da lavorare in base al tipo di lama
|
||||
-- se non arrivano dall'esterno si cercano i migliori disponibili
|
||||
-- se non arrivano dall'esterno si cercano i migliori disponibili, dapprima ignorando il flag bAllowFastCuts
|
||||
local EdgeToMachineList = OptionalParameters.EdgeToMachineList
|
||||
or {
|
||||
Top = GetEdgeToMachine( FaceToMachine.Edges, FaceToMachine.vtN, 'Top', bAllowFastCuts),
|
||||
Bottom = GetEdgeToMachine( FaceToMachine.Edges, FaceToMachine.vtN, 'Bottom', bAllowFastCuts),
|
||||
TopDownUp = GetEdgeToMachine( FaceToMachine.Edges, FaceToMachine.vtN, 'TopDownUp', bAllowFastCuts),
|
||||
TopGuillotine = GetEdgeToMachine( FaceToMachine.Edges, FaceToMachine.vtN, 'TopGuillotine', bAllowFastCuts)
|
||||
Top = GetEdgeToMachine( FaceToMachine.Edges, 'Top'),
|
||||
Bottom = GetEdgeToMachine( FaceToMachine.Edges, 'Bottom'),
|
||||
TopGuillotine = GetEdgeToMachine( FaceToMachine.Edges, 'TopGuillotine')
|
||||
}
|
||||
|
||||
local sChosenBladeType
|
||||
|
||||
-- se nToolIndex è presente, GetBestBlade sceglierà solo il lato, altrimenti sceglierà lama e lato
|
||||
local OptionalParametersGetBestBlade = {
|
||||
dElevationTop = EdgeToMachineList.Top.dElevation + BeamData.CUT_EXTRA,
|
||||
dElevationBottom = EdgeToMachineList.Bottom.dElevation + BeamData.CUT_EXTRA,
|
||||
dElevationTopDownUp = EdgeToMachineList.TopDownUp.dElevation + BeamData.CUT_EXTRA,
|
||||
EdgeToMachineTop = EdgeToMachineList.Top,
|
||||
EdgeToMachineBottom = EdgeToMachineList.Bottom,
|
||||
nToolIndex = nToolIndex
|
||||
}
|
||||
-- se nToolIndex è presente, GetBestBlade sceglierà solo il lato, altrimenti sceglierà lama e lato
|
||||
nToolIndex, sChosenBladeType = GetBestBlade( Proc, Part, FaceToMachine, OptionalParametersGetBestBlade)
|
||||
|
||||
-- se non è stato trovato un utensile e utensile e lati non arrivavano dall'esterno, si prova a cambiare lato (si prende il secondo della lista), sempre ignorando bAllowFastCuts
|
||||
if not nToolIndex and not OptionalParameters.nToolIndex and not OptionalParameters.EdgeToMachineList then
|
||||
EdgeToMachineList.Top = GetEdgeToMachine( FaceToMachine.Edges, 'Top', { nIndex = 2})
|
||||
EdgeToMachineList.Bottom = GetEdgeToMachine( FaceToMachine.Edges, 'Bottom', { nIndex = 2})
|
||||
OptionalParametersGetBestBlade.EdgeToMachineTop = EdgeToMachineList.Top
|
||||
OptionalParametersGetBestBlade.EdgeToMachineBottom = EdgeToMachineList.Bottom
|
||||
|
||||
nToolIndex, sChosenBladeType = GetBestBlade( Proc, Part, FaceToMachine, OptionalParametersGetBestBlade)
|
||||
end
|
||||
|
||||
-- se ancora non è stato trovato un utensile e utensile e lati non arrivavano dall'esterno, se permesso, si prova a scegliere il primo lato a minor elevazione (bAllowFastCuts)
|
||||
if bAllowFastCuts and not nToolIndex and not OptionalParameters.nToolIndex and not OptionalParameters.EdgeToMachineList then
|
||||
EdgeToMachineList.Top = GetEdgeToMachine( FaceToMachine.Edges, 'Top', { bAllowFastCuts = true})
|
||||
EdgeToMachineList.Bottom = GetEdgeToMachine( FaceToMachine.Edges, 'Bottom', { bAllowFastCuts = true})
|
||||
OptionalParametersGetBestBlade.EdgeToMachineTop = EdgeToMachineList.Top
|
||||
OptionalParametersGetBestBlade.EdgeToMachineBottom = EdgeToMachineList.Bottom
|
||||
|
||||
nToolIndex, sChosenBladeType = GetBestBlade( Proc, Part, FaceToMachine, OptionalParametersGetBestBlade)
|
||||
sChosenBladeType = sChosenBladeType .. 'Fast'
|
||||
end
|
||||
|
||||
|
||||
-- se ancora non è stato trovato un utensile e utensile e lati non arrivavano dall'esterno, se permesso, si prova a scegliere il secondo lato a minor elevazione (bAllowFastCuts)
|
||||
if bAllowFastCuts and not nToolIndex and not OptionalParameters.nToolIndex and not OptionalParameters.EdgeToMachineList then
|
||||
EdgeToMachineList.Top = GetEdgeToMachine( FaceToMachine.Edges, 'Top', { bAllowFastCuts = true, nIndex = 2})
|
||||
EdgeToMachineList.Bottom = GetEdgeToMachine( FaceToMachine.Edges, 'Bottom', { bAllowFastCuts = true, nIndex = 2})
|
||||
OptionalParametersGetBestBlade.EdgeToMachineTop = EdgeToMachineList.Top
|
||||
OptionalParametersGetBestBlade.EdgeToMachineBottom = EdgeToMachineList.Bottom
|
||||
|
||||
nToolIndex, sChosenBladeType = GetBestBlade( Proc, Part, FaceToMachine, OptionalParametersGetBestBlade)
|
||||
sChosenBladeType = sChosenBladeType .. 'Fast'
|
||||
end
|
||||
|
||||
-- se possibile, upgrade del taglio tipo 'Top' a taglio a ghigliottina. Si tenta anche se il taglio singolo non è riuscito.
|
||||
if ( sChosenBladeType == 'Top' or not nToolIndex) and bReduceBladePath and FaceData.IsFaceRectangular( Proc, FaceToMachine.id) then
|
||||
if ( sChosenBladeType == 'Top' or not nToolIndex) and bReduceBladePath and FaceData.IsFaceRectangle( FaceToMachine) then
|
||||
local nToolIndexGuillotine
|
||||
|
||||
-- ricerca lama migliore testa sopra
|
||||
local ToolInfo = MachiningLib.FindBlade( Proc, {
|
||||
vtN = FaceToMachine.vtN,
|
||||
bAllowTopHead = true,
|
||||
bAllowBottomHead = false
|
||||
bAllowBottomHead = false,
|
||||
FaceToMachine = FaceToMachine,
|
||||
EdgeToMachine = EdgeToMachineList.TopGuillotine,
|
||||
Part = Part
|
||||
})
|
||||
nToolIndexGuillotine = ToolInfo.nToolIndex
|
||||
|
||||
-- se non trovato utensile, si prova in DownUp
|
||||
if not nToolIndexGuillotine then
|
||||
ToolInfo = MachiningLib.FindBlade( Proc, {
|
||||
vtN = -FaceToMachine.vtN,
|
||||
bAllowTopHead = true,
|
||||
bAllowBottomHead = false})
|
||||
if ToolInfo.nToolIndex then
|
||||
local dMinNzDownUp = TOOLS[ToolInfo.nToolIndex].SetupInfo.GetMinNzDownUp( Part.b3Raw, FaceToMachine.vtN, EdgeToMachineList.TopGuillotine.vtN, TOOLS[ToolInfo.nToolIndex])
|
||||
if FaceToMachine.vtN:getZ() < dMinNzDownUp then
|
||||
nToolIndexGuillotine = ToolInfo.nToolIndex
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
-- test fattibilità taglio a ghigliottina
|
||||
if nToolIndexGuillotine then
|
||||
local dRadialOffset = FaceByBlade.GetRadialOffsetForGuillotine( nToolIndexGuillotine, EdgeToMachineList.TopGuillotine.dLength)
|
||||
@@ -437,7 +442,7 @@ local function GetSingleCutStrategy( Proc, Part, OptionalParameters)
|
||||
end
|
||||
|
||||
|
||||
local function GetDualSideCutStrategy( Proc, OptionalParameters)
|
||||
local function GetDualSideCutStrategy( Proc, Part, OptionalParameters)
|
||||
|
||||
-- parametri opzionali
|
||||
OptionalParameters = OptionalParameters or {}
|
||||
@@ -449,7 +454,7 @@ local function GetDualSideCutStrategy( Proc, OptionalParameters)
|
||||
|
||||
-- se possibile, si prova il doppio taglio orizzontale con mix testa sopra/sotto (questa modalità si esclude se l'utensile arriva dall'esterno)
|
||||
-- TODO valutare se farlo anche doppio orizzontale solo con testa sopra, se la lama ha la corsa per andare sotto!
|
||||
EdgeToMachine = GetEdgeToMachine( FaceToMachine.Edges, FaceToMachine.vtN, 'HorizontalBottom')
|
||||
EdgeToMachine = GetEdgeToMachine( FaceToMachine.Edges, 'HorizontalBottom')
|
||||
if not nToolIndex and AreSameOrOppositeVectorApprox( EdgeToMachine.vtN, Z_AX()) then
|
||||
|
||||
-- inizialmente si prova a lavorare in mezzeria
|
||||
@@ -458,17 +463,22 @@ local function GetDualSideCutStrategy( Proc, OptionalParameters)
|
||||
|
||||
-- ricerca lama testa sopra
|
||||
local ToolInfoTopBlade = MachiningLib.FindBlade( Proc, {
|
||||
vtN = FaceToMachine.vtN,
|
||||
bAllowTopHead = true,
|
||||
bAllowBottomHead = false,
|
||||
dElevation = dDepthToMachineTop
|
||||
dElevation = dDepthToMachineTop,
|
||||
FaceToMachine = FaceToMachine,
|
||||
EdgeToMachine = EdgeToMachine,
|
||||
Part = Part
|
||||
})
|
||||
-- ricerca lama testa sotto
|
||||
-- lavorando dalla direzione opposta si verifica come se si lavorasse il lato opposto
|
||||
local ToolInfoBottomBlade = MachiningLib.FindBlade( Proc, {
|
||||
vtN = FaceToMachine.vtN,
|
||||
bAllowTopHead = false,
|
||||
bAllowBottomHead = true,
|
||||
dElevation = dDepthToMachineBottom
|
||||
dElevation = dDepthToMachineBottom,
|
||||
FaceToMachine = FaceToMachine,
|
||||
EdgeToMachine = BeamLib.FindEdgeBestOrientedAsDirection( FaceToMachine.Edges, -EdgeToMachine.vtN),
|
||||
Part = Part
|
||||
})
|
||||
|
||||
local bIsTopLimited = ToolInfoTopBlade.dResidualDepth > 10 * GEO.EPS_SMALL
|
||||
@@ -480,11 +490,14 @@ local function GetDualSideCutStrategy( Proc, OptionalParameters)
|
||||
dDepthToMachineTop = TOOLS[ToolInfoTopBlade.nToolIndex].dMaxMaterial
|
||||
dDepthToMachineBottom = EdgeToMachine.dElevation - dDepthToMachineTop + BeamData.CUT_EXTRA_MIN
|
||||
-- ricerca lama sotto con la nuova depth
|
||||
-- lavorando dalla direzione opposta si verifica come se si lavorasse il lato opposto
|
||||
ToolInfoBottomBlade = MachiningLib.FindBlade( Proc, {
|
||||
vtN = FaceToMachine.vtN,
|
||||
bAllowTopHead = false,
|
||||
bAllowBottomHead = true,
|
||||
dElevation = dDepthToMachineBottom
|
||||
dElevation = dDepthToMachineBottom,
|
||||
FaceToMachine = FaceToMachine,
|
||||
EdgeToMachine = BeamLib.FindEdgeBestOrientedAsDirection( FaceToMachine.Edges, -EdgeToMachine.vtN),
|
||||
Part = Part
|
||||
})
|
||||
bIsBottomLimited = ToolInfoBottomBlade.dResidualDepth > 10 * GEO.EPS_SMALL
|
||||
|
||||
@@ -495,10 +508,12 @@ local function GetDualSideCutStrategy( Proc, OptionalParameters)
|
||||
dDepthToMachineTop = EdgeToMachine.dElevation - dDepthToMachineBottom + BeamData.CUT_EXTRA_MIN
|
||||
-- ricerca lama sopra con la nuova depth
|
||||
ToolInfoTopBlade = MachiningLib.FindBlade( Proc, {
|
||||
vtN = FaceToMachine.vtN,
|
||||
bAllowTopHead = true,
|
||||
bAllowBottomHead = false,
|
||||
dElevation = dDepthToMachineTop
|
||||
dElevation = dDepthToMachineTop,
|
||||
FaceToMachine = FaceToMachine,
|
||||
EdgeToMachine = EdgeToMachine,
|
||||
Part = Part
|
||||
})
|
||||
bIsTopLimited = ToolInfoTopBlade.dResidualDepth > 10 * GEO.EPS_SMALL
|
||||
end
|
||||
@@ -521,19 +536,29 @@ local function GetDualSideCutStrategy( Proc, OptionalParameters)
|
||||
end
|
||||
|
||||
-- arrivati qui si prova il taglio doppio verticale (taglio doppio orizzontale non si può fare oppure non ci arriva)
|
||||
EdgeToMachine = GetEdgeToMachine( FaceToMachine.Edges, FaceToMachine.vtN, 'Vertical')
|
||||
EdgeToMachine = GetEdgeToMachine( FaceToMachine.Edges, 'Vertical')
|
||||
local dDepthToMachine = EdgeToMachine.dElevation / 2 + BeamData.CUT_EXTRA_MIN
|
||||
|
||||
-- ricerca lama testa sopra
|
||||
local ToolInfo = MachiningLib.FindBlade( Proc, {
|
||||
vtN = FaceToMachine.vtN,
|
||||
bAllowTopHead = true,
|
||||
bAllowBottomHead = false,
|
||||
dElevation = dDepthToMachine
|
||||
dElevation = dDepthToMachine,
|
||||
FaceToMachine = FaceToMachine,
|
||||
EdgeToMachine = EdgeToMachine,
|
||||
Part = Part
|
||||
})
|
||||
|
||||
-- se lama ci arriva si assegnano utensili e profondità da ritornare
|
||||
if ToolInfo.nToolIndex and ToolInfo.dResidualDepth < 10 * GEO.EPS_SMALL then
|
||||
|
||||
-- lavorando dalla direzione opposta si verifica come se si lavorasse il lato opposto
|
||||
local EdgeToMachineOpposite = BeamLib.FindEdgeBestOrientedAsDirection( FaceToMachine.Edges, -EdgeToMachine.vtN)
|
||||
local bIsApplicableOpposite = MachiningLib.GetBladeEngagement( FaceToMachine, EdgeToMachineOpposite, Part, TOOLS[ToolInfo.nToolIndex], dDepthToMachine)
|
||||
if not bIsApplicableOpposite then
|
||||
return CuttingParametersList, EdgeToMachine
|
||||
end
|
||||
|
||||
-- si deve decidere se fare per primo il taglio opposto oppure no
|
||||
local bIsOppositeCutFirst = false
|
||||
local vtTemp = EdgeToMachine.vtN ^ FaceToMachine.vtN
|
||||
@@ -596,18 +621,18 @@ local function CutWholeWaste( Proc, Part, OptionalParameters)
|
||||
dExtendAfterTail = dExtendAfterTail,
|
||||
bReduceBladePath = bReduceBladePath
|
||||
}
|
||||
if sChosenBladeType == 'Top' or sChosenBladeType == 'Bottom' then
|
||||
if sChosenBladeType ~= 'TopGuillotine' then
|
||||
OptionalParametersFaceByBlade.OppositeToolDirectionMode = 'Optimized'
|
||||
end
|
||||
|
||||
Cutting = FaceByBlade.Make( Proc, Part, Proc.Faces[1], EdgeToMachine, OptionalParametersFaceByBlade)
|
||||
|
||||
-- se taglio da un lato non ce la fa, si prova da due lati
|
||||
-- TODO valutare se estendere ai non parallelogrammi
|
||||
elseif FaceData.IsFaceRhomboid( Proc, Proc.Faces[1].id) then
|
||||
-- TODO valutare se deve funzionare solo per i rettangoli
|
||||
elseif FaceData.IsFaceParallelogram( Proc.Faces[1]) then
|
||||
|
||||
local CuttingParametersList
|
||||
CuttingParametersList, EdgeToMachine = GetDualSideCutStrategy( Proc, OptionalParameters)
|
||||
CuttingParametersList, EdgeToMachine = GetDualSideCutStrategy( Proc, Part, OptionalParameters)
|
||||
|
||||
if CuttingParametersList then
|
||||
local OptionalParametersFaceByBlade = {
|
||||
@@ -633,6 +658,27 @@ local function CutWholeWaste( Proc, Part, OptionalParameters)
|
||||
end
|
||||
end
|
||||
|
||||
-- se nessun taglio è riuscito si riprova il taglio singolo permettendo i lati a minor elevazione, abbassando la qualità
|
||||
if not ( Cutting and Cutting.bIsApplicable) or ( CuttingDouble and not CuttingDouble.bIsApplicable) then
|
||||
|
||||
OptionalParameters.bAllowFastCuts = true
|
||||
nToolIndex, EdgeToMachine, sChosenBladeType = GetSingleCutStrategy( Proc, Part, OptionalParameters)
|
||||
|
||||
if nToolIndex then
|
||||
local OptionalParametersFaceByBlade = {
|
||||
dDepthToMachine = EdgeToMachine.dElevation + BeamData.CUT_EXTRA,
|
||||
nToolIndex = nToolIndex,
|
||||
dExtendAfterTail = dExtendAfterTail,
|
||||
bReduceBladePath = bReduceBladePath
|
||||
}
|
||||
if sChosenBladeType ~= 'TopGuillotine' then
|
||||
OptionalParametersFaceByBlade.OppositeToolDirectionMode = 'Optimized'
|
||||
end
|
||||
|
||||
Cutting = FaceByBlade.Make( Proc, Part, Proc.Faces[1], EdgeToMachine, OptionalParametersFaceByBlade)
|
||||
end
|
||||
end
|
||||
|
||||
if Cutting and Cutting.bIsApplicable then
|
||||
table.insert( Machinings, Cutting)
|
||||
dCompletionPercentage = Cutting.dCompletionPercentage or dCompletionPercentage
|
||||
@@ -654,6 +700,10 @@ local function CutWholeWaste( Proc, Part, OptionalParameters)
|
||||
Result.dCompletionPercentage = dCompletionPercentage
|
||||
Result.dCompletionIndex = FeatureLib.GetFeatureCompletionIndex( dCompletionPercentage)
|
||||
Result.dQuality = FeatureLib.GetStrategyQuality( Machinings)
|
||||
-- per tagli con lati brutti o ghigliottina si abbassa la qualità
|
||||
if ( sChosenBladeType ~= 'Top') and ( sChosenBladeType ~= 'Bottom') then
|
||||
Result.dQuality = FeatureLib.GetStrategyQuality( 'STD')
|
||||
end
|
||||
Result.dTimeToMachine = FeatureLib.GetStrategyTimeToMachine( Machinings)
|
||||
Result.dMRR = ( FeatureInfo.dFeatureVolume / Result.dTimeToMachine) / pow( 10, 6)
|
||||
else
|
||||
@@ -704,9 +754,6 @@ local function CutWithDicing( Proc, Part, OptionalParameters)
|
||||
return Machinings, Result
|
||||
end
|
||||
|
||||
-- limite per taglio DownUp
|
||||
local dMinNzDownUp = TOOLS[nToolIndex].SetupInfo.GetMinNzDownUp( Part.b3Raw, Face1.vtN, nil, TOOLS[nToolIndex])
|
||||
|
||||
-- calcolo dimensione cubetto e eventuale cubetto ridotto (tagli orizzontali con affondamento verticale)
|
||||
local dDiceDimension = min( TOOLS[nToolIndex].dMaxMaterial, BeamData.MAX_DIM_DICE)
|
||||
local dDiceDimensionReduced = dDiceDimension
|
||||
@@ -719,8 +766,8 @@ local function CutWithDicing( Proc, Part, OptionalParameters)
|
||||
OptionalParametersDiceCut.dOffsetParallel = dDiceDimension
|
||||
OptionalParametersDiceCut.dOffsetOrthogonal = dDiceDimension
|
||||
OptionalParametersDiceCut.dOffsetOrthogonalReduced = dDiceDimensionReduced
|
||||
OptionalParametersDiceCut.dMinNzDownUp = dMinNzDownUp
|
||||
OptionalParametersDiceCut.b3BoxDicing = b3BoxDicing
|
||||
OptionalParametersDiceCut.bSaveAddedGeometries = bSaveAddedGeometries
|
||||
local vCuts = DiceCut.GetDice( Part, Face1, Face2, OptionalParametersDiceCut)
|
||||
|
||||
-- se nessun cubetto trovato, si richiama ricorsivamente la BladeToWaste forzando di non fare i cubetti
|
||||
@@ -737,7 +784,7 @@ local function CutWithDicing( Proc, Part, OptionalParameters)
|
||||
local bAreOrthogonalCutsInverted = false
|
||||
for i = 1, #vCuts do
|
||||
for j = 1, #vCuts[i] do
|
||||
SetDiceFaceInfo( Proc, vCuts[i][j], bSaveAddedGeometries)
|
||||
SetDiceFaceInfo( Proc, vCuts[i][j])
|
||||
if ( i % 2) == 1 then
|
||||
local vtO = EgtSurfTmFacetNormVersor( vCuts[i][j], 0, GDB_ID.ROOT)
|
||||
if ( Face1.vtN:getY() > 0.766 and vtO:getY() < -0.05) or
|
||||
@@ -780,8 +827,7 @@ local function CutWithDicing( Proc, Part, OptionalParameters)
|
||||
-- scelta lato da lavorare per stabilire la vtToolDirection
|
||||
local EdgeToMachine = {}
|
||||
local _, Edges = FaceData.GetEdgesInfo( vCuts[i][1], 0)
|
||||
local vtNCurrentFace = EgtSurfTmFacetNormVersor( vCuts[i][1], 0, GDB_ID.ROOT)
|
||||
EdgeToMachine = GetEdgeToMachine( Edges, vtNCurrentFace, sChosenBladeType)
|
||||
EdgeToMachine = GetEdgeToMachine( Edges, sChosenBladeType)
|
||||
vtToolDirection = EdgeToMachine.vtN
|
||||
end
|
||||
end
|
||||
@@ -815,80 +861,47 @@ local function CutWithDicing( Proc, Part, OptionalParameters)
|
||||
-- caso standard (tagli perpendicolari o paralleli non accorpabili)
|
||||
if ( not bCanMergeParallelCuts) or ( not bIsDicingOk) then
|
||||
for j = 1, #vCuts[i] do
|
||||
local Cutting = {}
|
||||
local vtNCurrentFace = EgtSurfTmFacetNormVersor( vCuts[i][j], 0, GDB_ID.ROOT)
|
||||
local FaceToMachine = { id = 0, vtN = vtNCurrentFace}
|
||||
-- se taglio DownUp e strato pari composto da 1 o 2 elementi (tutti gli altri casi vengono saltati)
|
||||
if ( vtNCurrentFace:getZ() < dMinNzDownUp) and ( ( i % 2) == 0) and ( #vCuts[i] <= 2) then
|
||||
-- il primo elemento prende la direzione prevista, il secondo quella opposta
|
||||
local vtToolDirectionNew = Vector3d( vtToolDirection)
|
||||
if j ~= 1 then
|
||||
vtToolDirectionNew = -vtToolDirection
|
||||
end
|
||||
-- lavorazione
|
||||
local ProcTrimesh = FeatureLib.GetProcFromTrimesh( vCuts[i][j], Part)
|
||||
local _, Edges = FaceData.GetEdgesInfo( vCuts[i][j], 0)
|
||||
local EdgeToMachine = BeamLib.FindEdgeBestOrientedAsDirection( Edges, vtToolDirectionNew)
|
||||
local dDepthToMachine = EdgeToMachine.dElevation + BeamData.CUT_EXTRA
|
||||
local OptionalParametersFaceByBlade = {
|
||||
dDepthToMachine = dDepthToMachine,
|
||||
nToolIndex = nToolIndex,
|
||||
dRadialStepSpan = 0,
|
||||
dExtendAfterTail = dExtendAfterTail
|
||||
}
|
||||
Cutting = FaceByBlade.Make( ProcTrimesh, Part, FaceToMachine, EdgeToMachine, OptionalParametersFaceByBlade)
|
||||
Cutting.ptCenter = Point3d( ProcTrimesh.Faces[1].ptCenter:getX(), 0, 0)
|
||||
|
||||
if Cutting.bIsApplicable then
|
||||
table.insert( Machinings, Cutting)
|
||||
else
|
||||
bIsDicingOk = false
|
||||
end
|
||||
if Cutting.sStage == 'AfterTail' then
|
||||
bMoveAfterSplit = true
|
||||
end
|
||||
-- caso generale
|
||||
else
|
||||
-- in generale sta sollevato di pochissimo
|
||||
local dExtraCut = -0.1
|
||||
-- se tagli paralleli
|
||||
if ( i % 2) == 0 then
|
||||
-- se non ci sono tagli ortogonali devo affondare
|
||||
if bNoPerpCuts then
|
||||
-- in generale sta sollevato di pochissimo
|
||||
local dExtraCut = -0.1
|
||||
-- se tagli paralleli
|
||||
if ( i % 2) == 0 then
|
||||
-- se non ci sono tagli ortogonali devo affondare
|
||||
if bNoPerpCuts then
|
||||
dExtraCut = BeamData.CUT_EXTRA
|
||||
-- se è faccia singola si affonda
|
||||
elseif Proc.nFct < 2 then
|
||||
-- se tagli ortogonali invertiti, devo approfondire dello spessore lama
|
||||
if bAreOrthogonalCutsInverted then
|
||||
dExtraCut = TOOLS[nToolIndex].dThickness
|
||||
-- se ultimo taglio, devo affondare
|
||||
elseif j == #vCuts[i] then
|
||||
dExtraCut = BeamData.CUT_EXTRA
|
||||
-- se è faccia singola si affonda
|
||||
elseif Proc.nFct < 2 then
|
||||
-- se tagli ortogonali invertiti, devo approfondire dello spessore lama
|
||||
if bAreOrthogonalCutsInverted then
|
||||
dExtraCut = TOOLS[nToolIndex].dThickness
|
||||
-- se ultimo taglio, devo affondare
|
||||
elseif j == #vCuts[i] then
|
||||
dExtraCut = BeamData.CUT_EXTRA
|
||||
end
|
||||
end
|
||||
end
|
||||
local ProcTrimesh = FeatureLib.GetProcFromTrimesh( vCuts[i][j], Part)
|
||||
local _, Edges = FaceData.GetEdgesInfo( vCuts[i][j], 0)
|
||||
local EdgeToMachine = BeamLib.FindEdgeBestOrientedAsDirection( Edges, vtToolDirection)
|
||||
local dDepthToMachine = EdgeToMachine.dElevation + dExtraCut
|
||||
local OptionalParametersFaceByBlade = {
|
||||
dDepthToMachine = dDepthToMachine,
|
||||
nToolIndex = nToolIndex,
|
||||
dRadialStepSpan = 0,
|
||||
dExtendAfterTail = dExtendAfterTail
|
||||
}
|
||||
Cutting = FaceByBlade.Make( ProcTrimesh, Part, FaceToMachine, EdgeToMachine, OptionalParametersFaceByBlade)
|
||||
Cutting.ptCenter = Point3d( ProcTrimesh.Faces[1].ptCenter:getX(), 0, 0)
|
||||
end
|
||||
local Cutting = {}
|
||||
local ProcTrimesh = FeatureLib.GetProcFromTrimesh( vCuts[i][j], Part)
|
||||
local FaceToMachine = ProcTrimesh.Faces[1]
|
||||
local EdgeToMachine = BeamLib.FindEdgeBestOrientedAsDirection( FaceToMachine.Edges, vtToolDirection)
|
||||
local dDepthToMachine = EdgeToMachine.dElevation + dExtraCut
|
||||
local OptionalParametersFaceByBlade = {
|
||||
dDepthToMachine = dDepthToMachine,
|
||||
nToolIndex = nToolIndex,
|
||||
dRadialStepSpan = 0,
|
||||
dExtendAfterTail = dExtendAfterTail,
|
||||
bCollisionCheckForDownUpOnly = true
|
||||
}
|
||||
Cutting = FaceByBlade.Make( ProcTrimesh, Part, FaceToMachine, EdgeToMachine, OptionalParametersFaceByBlade)
|
||||
Cutting.ptCenter = Point3d( ProcTrimesh.Faces[1].ptCenter:getX(), 0, 0)
|
||||
|
||||
if Cutting.bIsApplicable then
|
||||
table.insert( Machinings, Cutting)
|
||||
bIsDicingOk = true
|
||||
else
|
||||
bIsDicingOk = false
|
||||
end
|
||||
if Cutting.sStage == 'AfterTail' then
|
||||
bMoveAfterSplit = true
|
||||
end
|
||||
if Cutting.bIsApplicable then
|
||||
table.insert( Machinings, Cutting)
|
||||
bIsDicingOk = true
|
||||
else
|
||||
bIsDicingOk = false
|
||||
end
|
||||
if Cutting.sStage == 'AfterTail' then
|
||||
bMoveAfterSplit = true
|
||||
end
|
||||
end
|
||||
end
|
||||
@@ -978,7 +991,7 @@ function BLADETOWASTE.Make( ProcOrId, Part, OptionalParameters)
|
||||
end
|
||||
end
|
||||
-- se due facce, cubetti troppo lunghi in X non si possono fare
|
||||
local ptEdge1, _, ptEdge2 = EgtSurfTmFacetOppositeSide( Proc.id, Proc.Faces[1].id, -Proc.Faces[1].Edges[nCommonEdge].vtN, GDB_ID.ROOT)
|
||||
local ptEdge1, ptEdge2 = Proc.Faces[1].Edges[nCommonEdge].ptStart, Proc.Faces[1].Edges[nCommonEdge].ptEnd
|
||||
local b3BoxEdge = BBox3d( ptEdge1, ptEdge2)
|
||||
local dEdgeLengthOnX = b3BoxEdge:getDimX()
|
||||
if FeatureLib.IsMachiningLong( dEdgeLengthOnX, Part) then
|
||||
@@ -1021,13 +1034,14 @@ function BLADETOWASTE.Make( ProcOrId, Part, OptionalParameters)
|
||||
-- TODO qui sostituire con check topologia DoubleBevel
|
||||
if dAngleBetweenFaces > 10 * GEO.EPS_SMALL then
|
||||
-- si creano superfici singole per le facce, estese fino al box della parte
|
||||
local nAddGrpId = BeamLib.GetAddGroup( Part.id)
|
||||
local idFace1 = EgtSurfTmPlaneInBBox( nAddGrpId, Proc.Faces[1].ptCenter, Proc.Faces[1].vtN, Part.b3Part, GDB_ID.ROOT)
|
||||
local idFace2 = EgtSurfTmPlaneInBBox( nAddGrpId, Proc.Faces[2].ptCenter, Proc.Faces[2].vtN, Part.b3Part, GDB_ID.ROOT)
|
||||
if not bSaveAddedGeometries then
|
||||
EgtSetLevel( idFace1, GDB_LV.TEMP)
|
||||
EgtSetLevel( idFace2, GDB_LV.TEMP)
|
||||
local idAddGroup
|
||||
if bSaveAddedGeometries then
|
||||
idAddGroup = BeamLib.GetAddGroup( Part.id)
|
||||
else
|
||||
idAddGroup = BeamLib.GetTempGroup()
|
||||
end
|
||||
local idFace1 = EgtSurfTmPlaneInBBox( idAddGroup, Proc.Faces[1].ptCenter, Proc.Faces[1].vtN, Part.b3Part, GDB_ID.ROOT)
|
||||
local idFace2 = EgtSurfTmPlaneInBBox( idAddGroup, Proc.Faces[2].ptCenter, Proc.Faces[2].vtN, Part.b3Part, GDB_ID.ROOT)
|
||||
|
||||
-- lavorazione facce
|
||||
local Machinings1, Result1 = MakeOneFace( idFace1, Part, OptionalParameters)
|
||||
@@ -1074,10 +1088,10 @@ function BLADETOWASTE.Make( ProcOrId, Part, OptionalParameters)
|
||||
end
|
||||
|
||||
-- feature concava >= 90deg: lavorata con cubetti, se attivi
|
||||
elseif ( not bDisableDicing) and ( dAngleBetweenFaces >= -91) then
|
||||
elseif not ( bDisableDicing or FeatureInfo.bIsFeatureSmall) and ( dAngleBetweenFaces >= -91) then
|
||||
Machinings, Result = CutWithDicing( Proc, Part, OptionalParameters)
|
||||
|
||||
-- qui arrivano feature concave < 90deg, oppure >= 90deg con cubetti disabilitati: lavorata come 2 facce singole con accorciamento
|
||||
-- qui arrivano feature concave < 90deg, oppure >= 90deg con cubetti disabilitati: lavorata come 2 facce singole con eventuale accorciamento
|
||||
else
|
||||
-- per ogni faccia si calcola la lavorazione
|
||||
for i = 1, #Proc.Faces do
|
||||
@@ -1096,7 +1110,7 @@ function BLADETOWASTE.Make( ProcOrId, Part, OptionalParameters)
|
||||
local OptionalParametersGetSingleCutStrategy = {
|
||||
bReduceBladePath = false,
|
||||
nFaceToMachineIndex = i,
|
||||
EdgeToMachineList = { Top = EdgeToMachine, Bottom = EdgeToMachine, TopDownUp = EdgeToMachine}
|
||||
EdgeToMachineList = { Top = EdgeToMachine, Bottom = EdgeToMachine}
|
||||
}
|
||||
nToolIndex = GetSingleCutStrategy( Proc, Part, OptionalParametersGetSingleCutStrategy)
|
||||
end
|
||||
|
||||
+123
-74
@@ -16,8 +16,8 @@ local function GetLeadInOutType( Machining)
|
||||
local sLeadInOutType = ''
|
||||
|
||||
if Machining.bIsStartClosed or Machining.bIsEndClosed
|
||||
or Machining.sCutType == 'Guillotine'
|
||||
or Machining.sCutType == 'Reduced' then
|
||||
or Machining.sEdgeUsage == 'Guillotine'
|
||||
or Machining.sEdgeUsage == 'Reduced' then
|
||||
|
||||
sLeadInOutType = 'Perpendicular'
|
||||
else
|
||||
@@ -68,10 +68,10 @@ local function CalculateLeadInOut( Machining, EdgeToMachine, bIsSplitFeature)
|
||||
local dToolMarkLength = sqrt( Machining.dDepthToMachine * TOOLS[Machining.nToolIndex].dDiameter - Machining.dDepthToMachine * Machining.dDepthToMachine)
|
||||
-- allungamento per faccia singola (aperta in tutte le direzioni)
|
||||
local dAddedLengthOpenFace = BeamData.CUT_EXTRA
|
||||
if Machining.sCutType == 'Guillotine' then
|
||||
if Machining.sEdgeUsage == 'Guillotine' then
|
||||
local dGuillotineLengthToMachine = 1
|
||||
dAddedLengthOpenFace = ( - EdgeToMachine.dLength + dGuillotineLengthToMachine) / 2
|
||||
elseif Machining.sCutType == 'Reduced' then
|
||||
elseif Machining.sEdgeUsage == 'Reduced' then
|
||||
dAddedLengthOpenFace = - FACEBYBLADE.GetPathReductionLength( Machining.nToolIndex, Machining.dMaxRadialOffset)
|
||||
end
|
||||
|
||||
@@ -259,60 +259,50 @@ function FACEBYBLADE.Make( Proc, Part, FaceToMachine, EdgeToMachine, OptionalPar
|
||||
dLongitudinalOffset = 0
|
||||
end
|
||||
local dRadialStepSpan = OptionalParameters.dRadialStepSpan
|
||||
local dMinNzDownUp = OptionalParameters.dMinNzDownUp
|
||||
local sUserNotes = OptionalParameters.sUserNotes or ''
|
||||
local bCollisionCheckForDownUpOnly = OptionalParameters.bCollisionCheckForDownUpOnly or false
|
||||
|
||||
-- lunghezze, direzioni e punti caratteristici della lavorazione e del lato lavorato
|
||||
Cutting.dEdgeLength = EdgeToMachine.dLength
|
||||
if OppositeToolDirectionMode == 'Enabled' then
|
||||
Cutting.vtToolDirection = -EdgeToMachine.vtN
|
||||
else
|
||||
Cutting.vtToolDirection = EdgeToMachine.vtN
|
||||
end
|
||||
Cutting.vtEdgeDirection = EdgeToMachine.vtN ^ FaceToMachine.vtN
|
||||
-- TODO conviene spostare questi calcoli nel FaceData?
|
||||
Cutting.ptEdge1, _, Cutting.ptEdge2 = EgtSurfTmFacetOppositeSide( Proc.id, FaceToMachine.id, -Cutting.vtToolDirection, GDB_ID.ROOT)
|
||||
-- TODO gestire lama da sotto
|
||||
-- se si conosce il limite downUp (utensile forzato o downUp forzato) si decide se invertire (ToolInvert)
|
||||
-- TODO esiste un limite downUp massimo per la lama da sopra??
|
||||
if nToolIndex and not dMinNzDownUp then
|
||||
dMinNzDownUp = TOOLS[nToolIndex].SetupInfo.GetMinNzDownUp( Part.b3Raw, FaceToMachine.vtN, Cutting.vtToolDirection, TOOLS[nToolIndex])
|
||||
end
|
||||
if dMinNzDownUp and FaceToMachine.vtN:getZ() < dMinNzDownUp then
|
||||
Cutting.bToolInvert = true
|
||||
else
|
||||
Cutting.bToolInvert = false
|
||||
end
|
||||
Cutting.vtToolDirection = EdgeToMachine.vtN
|
||||
Cutting.ptEdge1, Cutting.ptEdge2 = EdgeToMachine.ptStart, EdgeToMachine.ptEnd
|
||||
local EdgeToMachineOpposite = BeamLib.FindEdgeBestOrientedAsDirection( FaceToMachine.Edges, -EdgeToMachine.vtN)
|
||||
|
||||
-- ricerca utensile
|
||||
-- l'utensile arriva da fuori: si determina se il taglio è fattibile e il modo di lavorare della lama
|
||||
if nToolIndex then
|
||||
|
||||
Cutting.nToolIndex = nToolIndex
|
||||
Cutting.bIsApplicable, Cutting.sBladeEngagement, Cutting.bMoveAfterSplit = MachiningLib.GetBladeEngagement( FaceToMachine, EdgeToMachine, Part, TOOLS[Cutting.nToolIndex], dDepthToMachine, bCollisionCheckForDownUpOnly)
|
||||
|
||||
-- utensile da cercare: si prende la lama migliore che può effettuare questo taglio, senza particolari analisi
|
||||
else
|
||||
local ToolSearchParameters = {}
|
||||
ToolSearchParameters.dElevation = dDepthToMachine
|
||||
if Cutting.bToolInvert then
|
||||
ToolSearchParameters.vtN = -FaceToMachine.vtN
|
||||
else
|
||||
ToolSearchParameters.vtN = FaceToMachine.vtN
|
||||
end
|
||||
ToolSearchParameters.bAllowTopHead = true
|
||||
-- TODO bisognerà implementare anche la lama da sotto
|
||||
ToolSearchParameters.bAllowBottomHead = false
|
||||
ToolSearchParameters.bAllowBottomHead = true
|
||||
ToolSearchParameters.bForceLongcutBlade = bForceLongcutBlade
|
||||
ToolSearchParameters.FaceToMachine = FaceToMachine
|
||||
ToolSearchParameters.EdgeToMachine = EdgeToMachine
|
||||
ToolSearchParameters.Part = Part
|
||||
|
||||
local ToolInfo = MachiningLib.FindBlade( Proc, ToolSearchParameters)
|
||||
-- ora che l'utensile è scelto, se non era definito l'angolo di DownUp lo verifico per decidere se invertire
|
||||
if ToolInfo.nToolIndex and not dMinNzDownUp then
|
||||
dMinNzDownUp = TOOLS[ToolInfo.nToolIndex].SetupInfo.GetMinNzDownUp( Part.b3Raw, FaceToMachine.vtN, Cutting.vtToolDirection, TOOLS[ToolInfo.nToolIndex])
|
||||
if FaceToMachine.vtN:getZ() < dMinNzDownUp then
|
||||
Cutting.bToolInvert = true
|
||||
end
|
||||
end
|
||||
Cutting.nToolIndex = ToolInfo.nToolIndex
|
||||
Cutting.sBladeEngagement = ToolInfo.sBladeEngagement
|
||||
Cutting.bMoveAfterSplit = ToolInfo.bMoveAfterSplit
|
||||
|
||||
-- se non trovato utensile, la lavorazione non è applicabile
|
||||
if not Cutting.nToolIndex then
|
||||
Cutting.bIsApplicable = false
|
||||
end
|
||||
end
|
||||
if not TOOLS[Cutting.nToolIndex] or not TOOLS[Cutting.nToolIndex].sName then
|
||||
|
||||
-- orientamento non raggiungibile o lama non trovata: non applicabile
|
||||
if not Cutting.bIsApplicable then
|
||||
Cutting.sMessage = 'Blade not found'
|
||||
Cutting.bIsApplicable = false
|
||||
EgtOutLog( Cutting.sMessage)
|
||||
|
||||
return Cutting, EdgeToMachine.dElevation
|
||||
end
|
||||
|
||||
@@ -322,6 +312,7 @@ function FACEBYBLADE.Make( Proc, Part, FaceToMachine, EdgeToMachine, OptionalPar
|
||||
Cutting.sMessage = 'Pocket too narrow for blade thickness'
|
||||
Cutting.bIsApplicable = false
|
||||
EgtOutLog( Cutting.sMessage)
|
||||
|
||||
return Cutting, EdgeToMachine.dElevation
|
||||
end
|
||||
-- se tasca chiusa da entrambi i lati e più stretta della lama la lavorazione non è applicabile
|
||||
@@ -330,16 +321,20 @@ function FACEBYBLADE.Make( Proc, Part, FaceToMachine, EdgeToMachine, OptionalPar
|
||||
Cutting.sMessage = 'Pocket too narrow for blade diameter'
|
||||
Cutting.bIsApplicable = false
|
||||
EgtOutLog( Cutting.sMessage)
|
||||
|
||||
return Cutting, EdgeToMachine.dElevation
|
||||
end
|
||||
end
|
||||
|
||||
-- parametri della lavorazione
|
||||
|
||||
-- profondità (parametro DEPTH)
|
||||
Cutting.sDepth = sDepth
|
||||
|
||||
-- inizio e fine aperti o chiusi
|
||||
Cutting.bIsStartClosed = not EdgeToMachine.bIsStartOpen
|
||||
Cutting.bIsEndClosed = not EdgeToMachine.bIsEndOpen
|
||||
|
||||
-- lato di lavoro e inversione per avere taglio concorde
|
||||
if TOOLS[Cutting.nToolIndex].bIsCCW then
|
||||
Cutting.nWorkside = MCH_MILL_WS.RIGHT
|
||||
@@ -348,37 +343,59 @@ function FACEBYBLADE.Make( Proc, Part, FaceToMachine, EdgeToMachine, OptionalPar
|
||||
Cutting.nWorkside = MCH_MILL_WS.LEFT
|
||||
Cutting.bInvert = false
|
||||
end
|
||||
-- se OppositeToolDirectionMode è Optimized, se possibile e necessario, si attiva per garantire taglio concorde e verso l'alto (massima qualità)
|
||||
if ( OppositeToolDirectionMode == 'Optimized') and ( Proc.nFct == 1) and ( FaceData.IsFaceRhomboid( Proc, FaceToMachine.id)) then
|
||||
OppositeToolDirectionMode = 'Disabled'
|
||||
-- la direzione di percorrenza del lato deve essere verso l'alto; bInvert va considerata perchè inverte la direzione di percorrenza.
|
||||
if ( Cutting.bInvert and Cutting.vtEdgeDirection:getZ() > 100 * GEO.EPS_SMALL)
|
||||
or ( ( not Cutting.bInvert) and Cutting.vtEdgeDirection:getZ() < -100 * GEO.EPS_SMALL) then
|
||||
|
||||
-- si attiva OppositeToolDirection solo se non cambiano le condizioni di taglio downUp
|
||||
local dNewMinNzDownUp = TOOLS[nToolIndex].SetupInfo.GetMinNzDownUp( Part.b3Raw, FaceToMachine.vtN, -Cutting.vtToolDirection, TOOLS[nToolIndex])
|
||||
if ( FaceToMachine.vtN:getZ() < dMinNzDownUp) == ( FaceToMachine.vtN:getZ() < dNewMinNzDownUp) then
|
||||
OppositeToolDirectionMode = 'Enabled'
|
||||
Cutting.vtToolDirection = -EdgeToMachine.vtN
|
||||
Cutting.ptEdge1, _, Cutting.ptEdge2 = EgtSurfTmFacetOppositeSide( Proc.id, FaceToMachine.id, -Cutting.vtToolDirection, GDB_ID.ROOT)
|
||||
Cutting.bInvert = not Cutting.bInvert
|
||||
-- se le condizioni downUp cambiano, si setta per tagliare verso l'alto
|
||||
else
|
||||
if Cutting.nWorkside == MCH_MILL_WS.RIGHT then
|
||||
Cutting.nWorkside = MCH_MILL_WS.LEFT
|
||||
Cutting.bInvert = false
|
||||
else
|
||||
Cutting.nWorkside = MCH_MILL_WS.RIGHT
|
||||
Cutting.bInvert = true
|
||||
end
|
||||
-- ToolInvert
|
||||
if Cutting.sBladeEngagement == 'DownUp' then
|
||||
Cutting.bToolInvert = true
|
||||
Cutting.bInvert = not Cutting.bInvert
|
||||
end
|
||||
|
||||
-- analisi fattibilità lavorazione dal lato opposto
|
||||
if OppositeToolDirectionMode ~= 'Disabled' then
|
||||
|
||||
-- lavorando dalla direzione opposta si verifica come se si lavorasse il lato opposto
|
||||
local bIsApplicableOpposite, sBladeEngagementOpposite, bMoveAfterSplit = MachiningLib.GetBladeEngagement( FaceToMachine, EdgeToMachineOpposite, Part, TOOLS[Cutting.nToolIndex], dDepthToMachine, bCollisionCheckForDownUpOnly)
|
||||
|
||||
-- taglio opposto non fattibile
|
||||
if not bIsApplicableOpposite then
|
||||
-- se richiesto, si ritorna non applicabile
|
||||
if OppositeToolDirectionMode == 'Enabled' then
|
||||
|
||||
Cutting.sMessage = 'Orientation not reachable'
|
||||
Cutting.bIsApplicable = false
|
||||
EgtOutLog( Cutting.sMessage)
|
||||
|
||||
return Cutting, EdgeToMachine.dElevation
|
||||
|
||||
-- se opzionale, si disabilita
|
||||
elseif OppositeToolDirectionMode == 'Optimized' then
|
||||
OppositeToolDirectionMode = 'Disabled'
|
||||
end
|
||||
end
|
||||
elseif OppositeToolDirectionMode == 'Enabled' then
|
||||
Cutting.bInvert = not Cutting.bInvert
|
||||
end
|
||||
if Cutting.bToolInvert then
|
||||
Cutting.bInvert = not Cutting.bInvert
|
||||
|
||||
-- se OppositeToolDirectionMode è Optimized, se possibile e necessario, si attiva la lavorazione dal lato opposto per garantire taglio concorde e verso l'alto (massima qualità)
|
||||
if ( OppositeToolDirectionMode == 'Optimized') and ( Proc.nFct == 1) and ( FaceData.IsFaceParallelogram( FaceToMachine)) then
|
||||
|
||||
OppositeToolDirectionMode = 'Disabled'
|
||||
|
||||
-- la direzione di percorrenza del lato deve essere verso l'alto; bInvert va considerata perchè inverte la direzione di percorrenza
|
||||
-- il BladeEngagement non deve cambiare, altrimenti è inutile invertire la direzione
|
||||
if ( sBladeEngagementOpposite == Cutting.sBladeEngagement)
|
||||
and ( bMoveAfterSplit == Cutting.bMoveAfterSplit)
|
||||
and ( Cutting.bInvert and Cutting.vtEdgeDirection:getZ() > 100 * GEO.EPS_SMALL)
|
||||
or ( ( not Cutting.bInvert) and Cutting.vtEdgeDirection:getZ() < -100 * GEO.EPS_SMALL) then
|
||||
|
||||
OppositeToolDirectionMode = 'Enabled'
|
||||
end
|
||||
end
|
||||
|
||||
if OppositeToolDirectionMode == 'Enabled' then
|
||||
Cutting.vtToolDirection = EdgeToMachineOpposite.vtN
|
||||
Cutting.ptEdge1, Cutting.ptEdge2 = EdgeToMachineOpposite.ptStart, EdgeToMachineOpposite.ptEnd
|
||||
Cutting.bInvert = not Cutting.bInvert
|
||||
end
|
||||
end
|
||||
|
||||
-- profondità da lavorare e offset radiale
|
||||
if OptionalParameters.dPocketHeight then
|
||||
if TOOLS[Cutting.nToolIndex].dMaxDepth > dDepthToMachine - 10 * GEO.EPS_SMALL then
|
||||
@@ -402,34 +419,56 @@ function FACEBYBLADE.Make( Proc, Part, FaceToMachine, EdgeToMachine, OptionalPar
|
||||
else
|
||||
Cutting.dDepthToMachine = dDepthToMachine
|
||||
Cutting.dResidualDepth = 0
|
||||
Cutting.sCutType = 'Standard'
|
||||
Cutting.sEdgeUsage = 'Standard'
|
||||
if bReduceBladePath
|
||||
and ( Proc.nFct == 1)
|
||||
and FaceData.IsFaceRectangular( Proc, FaceToMachine.id) then
|
||||
and FaceData.IsFaceRectangle( FaceToMachine) then
|
||||
|
||||
local bIsTopBlade = TOOLS[nToolIndex].SetupInfo.HeadType.bTop
|
||||
Cutting.dMaxRadialOffset = TOOLS[nToolIndex].dMaxMaterial - Cutting.dDepthToMachine - BeamData.CUT_SIC
|
||||
Cutting.dRadialOffsetGuillotine = FACEBYBLADE.GetRadialOffsetForGuillotine( nToolIndex, EdgeToMachine.dLength)
|
||||
-- TODO la lama sotto deve poter ridurre. Ghigliottina sì o no?
|
||||
local bIsTopBlade = TOOLS[Cutting.nToolIndex].SetupInfo.HeadType.bTop
|
||||
Cutting.dMaxRadialOffset = TOOLS[Cutting.nToolIndex].dMaxMaterial - Cutting.dDepthToMachine - BeamData.CUT_SIC
|
||||
Cutting.dRadialOffsetGuillotine = FACEBYBLADE.GetRadialOffsetForGuillotine( Cutting.nToolIndex, EdgeToMachine.dLength)
|
||||
if Cutting.dMaxRadialOffset > 10 * GEO.EPS_SMALL then
|
||||
-- taglio a ghigliottina
|
||||
if bIsTopBlade and ( Cutting.dRadialOffsetGuillotine < Cutting.dMaxRadialOffset - 10 * GEO.EPS_SMALL) then
|
||||
|
||||
dDepthToMachine = Cutting.dDepthToMachine + Cutting.dRadialOffsetGuillotine
|
||||
Cutting.sCutType = 'Guillotine'
|
||||
Cutting.sEdgeUsage = 'Guillotine'
|
||||
|
||||
-- taglio ridotto
|
||||
else
|
||||
dDepthToMachine = Cutting.dDepthToMachine + Cutting.dMaxRadialOffset
|
||||
Cutting.sCutType = 'Reduced'
|
||||
Cutting.sEdgeUsage = 'Reduced'
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
-- se cambiata la profondità dDepthToMachine, si ritesta la fattibilità del taglio
|
||||
if Cutting.sEdgeUsage ~= 'Standard' then
|
||||
local EdgeToMachineForEngagement = EdgeToMachine
|
||||
if OppositeToolDirectionMode == 'Enabled' then
|
||||
EdgeToMachineForEngagement = EdgeToMachineOpposite
|
||||
end
|
||||
local bIsApplicable, sBladeEngagement, bMoveAfterSplit = MachiningLib.GetBladeEngagement( FaceToMachine, EdgeToMachineForEngagement, Part, TOOLS[Cutting.nToolIndex], dDepthToMachine)
|
||||
|
||||
-- se non fattibile o cambiano le condizioni BladeEngagement, non si riduce
|
||||
if not ( bIsApplicable and ( sBladeEngagement == Cutting.sBladeEngagement) and ( bMoveAfterSplit == Cutting.bMoveAfterSplit)) then
|
||||
Cutting.sEdgeUsage = 'Standard'
|
||||
dDepthToMachine = Cutting.dDepthToMachine
|
||||
end
|
||||
end
|
||||
|
||||
-- offset radiale (cambia se taglio opposto)
|
||||
if OppositeToolDirectionMode == 'Enabled' then
|
||||
Cutting.dRadialOffset = -dDepthToMachine
|
||||
else
|
||||
Cutting.dRadialOffset = EdgeToMachine.dElevation - dDepthToMachine
|
||||
end
|
||||
end
|
||||
|
||||
-- completamento
|
||||
Cutting.dCompletionPercentage = ( 1 - Cutting.dResidualDepth / Cutting.dDepthToMachine) * 100
|
||||
|
||||
-- step verticale e offset longitudinale
|
||||
Cutting.Steps = MachiningLib.GetMachiningSteps( dPocketHeight, TOOLS[Cutting.nToolIndex].dThickness)
|
||||
Cutting.Steps.nStepType = MCH_MILL_ST.ONEWAY
|
||||
@@ -443,10 +482,13 @@ function FACEBYBLADE.Make( Proc, Part, FaceToMachine, EdgeToMachine, OptionalPar
|
||||
else
|
||||
Cutting.dLongitudinalOffset = dLongitudinalOffset
|
||||
end
|
||||
|
||||
-- distanza di sicurezza
|
||||
Cutting.dStartSafetyLength = BeamData.CUT_SIC
|
||||
|
||||
-- overlap
|
||||
Cutting.dOverlap = 0
|
||||
|
||||
-- EdgeUse e frame lavorazione
|
||||
if OppositeToolDirectionMode == 'Enabled' then
|
||||
Cutting.nFaceuse = BeamLib.GetNearestOrthoOpposite( -Cutting.vtToolDirection)
|
||||
@@ -457,10 +499,13 @@ function FACEBYBLADE.Make( Proc, Part, FaceToMachine, EdgeToMachine, OptionalPar
|
||||
--Cutting.vtFaceUse = Cutting.vtToolDirection
|
||||
Cutting.nEdgesFaceUse = EdgeToMachine.id
|
||||
end
|
||||
|
||||
-- SCC
|
||||
Cutting.nSCC = GetSCC( Cutting.vtToolDirection, Cutting.vtEdgeDirection, FaceToMachine.vtN)
|
||||
|
||||
-- asse bloccato
|
||||
Cutting.sBlockedAxis = BeamLib.GetBlockedAxis( Cutting.nToolIndex, 'perpendicular', Part.b3Raw, FaceToMachine.vtN, EgtIf( FaceToMachine.vtN:getX() > 0, X_AX(), -X_AX()))
|
||||
|
||||
-- eventuale step orizzontale
|
||||
Cutting.CloneStepsRadial = {}
|
||||
if not dRadialStepSpan then
|
||||
@@ -472,8 +517,10 @@ function FACEBYBLADE.Make( Proc, Part, FaceToMachine, EdgeToMachine, OptionalPar
|
||||
Cutting.CloneStepsRadial.nCount = 1
|
||||
Cutting.CloneStepsRadial.dStep = Cutting.dDepthToMachine
|
||||
end
|
||||
|
||||
-- approccio e retrazione
|
||||
Cutting.LeadIn, Cutting.LeadOut = CalculateLeadInOut( Cutting, EdgeToMachine, bIsSplitFeature)
|
||||
|
||||
-- lunghezza lavorata
|
||||
-- TODO per il calcolo del dLengthOnX si deve correggere con allungamento / accorciamento percorso
|
||||
Cutting.dLengthToMachine = EdgeToMachine.dLength + Cutting.LeadIn.dStartAddLength + Cutting.LeadOut.dEndAddLength
|
||||
@@ -500,7 +547,7 @@ function FACEBYBLADE.Make( Proc, Part, FaceToMachine, EdgeToMachine, OptionalPar
|
||||
-- se lavorazione aperta sulla coda, eventuali aggiustamenti
|
||||
-- TODO valutare se fare funzione a parte
|
||||
local bIsTruncatingCutOnTail = Proc.Topology and ( Proc.Topology.sName == 'Cut-1-Through' or Proc.Topology.sName == 'TailCut') and Proc.AffectedFaces.bLeft
|
||||
if bIsTruncatingCutOnTail then
|
||||
if Cutting.bMoveAfterSplit or bIsTruncatingCutOnTail then
|
||||
Cutting.sStage = 'AfterTail'
|
||||
elseif Proc.AffectedFaces.bLeft and ( EdgeToMachine.sType == 'Bottom' or ( Cutting.vtToolDirection:getX() < 0.707)) then
|
||||
local dLengthOnX = Cutting.dLengthOnX
|
||||
@@ -517,12 +564,14 @@ function FACEBYBLADE.Make( Proc, Part, FaceToMachine, EdgeToMachine, OptionalPar
|
||||
if not AreSameOrOppositeVectorApprox( EdgeToMachine.vtN, Y_AX()) then
|
||||
if MachiningLib.CanMoveAfterSplitcut( dLengthOnX, Part) then
|
||||
Cutting.sStage = 'AfterTail'
|
||||
Cutting.bMoveAfterSplit = true
|
||||
else
|
||||
Cutting.bIsApplicable = false
|
||||
end
|
||||
elseif dAddLengthLeftSide + dAddLengthToReduce > dExtendAfterTail then
|
||||
if MachiningLib.CanMoveAfterSplitcut( dLengthOnX, Part) then
|
||||
Cutting.sStage = 'AfterTail'
|
||||
Cutting.bMoveAfterSplit = true
|
||||
else
|
||||
if bStartLeft then
|
||||
Cutting.LeadIn.dStartAddLength = - dAddLengthToReduce + dExtendAfterTail
|
||||
|
||||
@@ -83,7 +83,7 @@ function FACEBYCHAINSAW.Make( Proc, Part, FaceToMachine, EdgeToMachine, Optional
|
||||
Mortising.vtToolDirection = EdgeToMachine.vtN
|
||||
end
|
||||
Mortising.vtEdgeDirection = EdgeToMachine.vtN ^ FaceToMachine.vtN
|
||||
Mortising.ptEdge1, _, Mortising.ptEdge2 = EgtSurfTmFacetOppositeSide( Proc.id, FaceToMachine.id, -Mortising.vtToolDirection, GDB_ID.ROOT)
|
||||
Mortising.ptEdge1, Mortising.ptEdge2 = EdgeToMachine.ptStart, EdgeToMachine.ptEnd
|
||||
|
||||
-- ricerca utensile
|
||||
local ToolSearchParameters = {}
|
||||
|
||||
@@ -204,8 +204,7 @@ function FACEBYMILL.Make( Proc, Part, FaceToMachine, EdgeToMachine, OptionalPara
|
||||
Milling.vtToolDirection = EdgeToMachine.vtN
|
||||
end
|
||||
Milling.vtEdgeDirection = EdgeToMachine.vtN ^ FaceToMachine.vtN
|
||||
-- TODO conviene spostare questi calcoli nel FaceData?
|
||||
Milling.ptEdge1, _, Milling.ptEdge2 = EgtSurfTmFacetOppositeSide( Proc.id, FaceToMachine.id, -Milling.vtToolDirection, GDB_ID.ROOT)
|
||||
Milling.ptEdge1, Milling.ptEdge2 = EdgeToMachine.ptStart, EdgeToMachine.ptEnd
|
||||
|
||||
-- se si conosce il limite downUp (utensile forzato o downUp forzato) si decide se invertire (ToolInvert)
|
||||
if nToolIndex and not dMinNzDownUp then
|
||||
|
||||
+2
-2
@@ -2,5 +2,5 @@
|
||||
-- Gestione della versione di Beam
|
||||
|
||||
NAME = 'Beam'
|
||||
VERSION = '2.6d1'
|
||||
MIN_EXE = '2.6g1'
|
||||
VERSION = '2.8a1'
|
||||
MIN_EXE = '2.7j2'
|
||||
|
||||
Reference in New Issue
Block a user