- in MachiningLib.FindBlade si restituisce il BladeEngagement, se presente

- in BLADETOWASTE.GetEdgeToMachine aggiunta la possibilità di restituire l'n-esimo lato della lista ordinata; in GetSingleCutStrategy si tenta di cambiare lato se il con il primo set non si è trovato alcun utensile; altre piccole correzioni
- in FACEBYBLADE refactoring per contemplare i vari casi di inversione
This commit is contained in:
luca.mazzoleni
2025-11-07 10:15:01 +01:00
parent 15db75dfad
commit 4ce77a4792
4 changed files with 80 additions and 41 deletions
+13 -3
View File
@@ -369,8 +369,9 @@ function MachiningLib.GetBladeEngagement( Face, Edge, Part, Tool, dDepthToMachin
end
-- rischio collisione carro Z: non lavorabile in Downup
local bIsToolBelowWorkpiece = Edge.vtN:getZ() < - 10 * GEO.EPS_SMALL
local bIsToolAboveWorkpiece = Edge.vtN:getZ() > 10 * GEO.EPS_SMALL
-- 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
@@ -536,6 +537,8 @@ function MachiningLib.FindBlade( Proc, ToolSearchParameters)
local nBestToolIndex
local dBestToolResidualDepth = 0
local sCurrentBladeEngagement
local sBestBladeEngagement
for i = 1, #TOOLS do
local bIsToolCompatible = false
@@ -552,7 +555,8 @@ function MachiningLib.FindBlade( Proc, ToolSearchParameters)
-- 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 = MachiningLib.GetBladeEngagement( FaceToMachine, EdgeToMachine, Part, TOOLS[i], dElevation, bCollisionCheckForDownUpOnly)
local bIsBladeOk = false
bIsBladeOk, sCurrentBladeEngagement = MachiningLib.GetBladeEngagement( FaceToMachine, EdgeToMachine, Part, TOOLS[i], dElevation, bCollisionCheckForDownUpOnly)
-- orientamento non raggiungibile
if not bIsBladeOk then
bIsToolCompatible = false
@@ -577,11 +581,13 @@ function MachiningLib.FindBlade( Proc, ToolSearchParameters)
if not nBestToolIndex or ( dBestToolResidualDepth > 0 and dCurrentResidualDepth <= 10 * GEO.EPS_SMALL) then
nBestToolIndex = i
dBestToolResidualDepth = dCurrentResidualDepth
sBestBladeEngagement = sCurrentBladeEngagement
else
-- 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
else
-- entrambi completi
if dBestToolResidualDepth <= 10 * GEO.EPS_SMALL and dCurrentResidualDepth <= 10 * GEO.EPS_SMALL then
@@ -592,11 +598,13 @@ function MachiningLib.FindBlade( Proc, ToolSearchParameters)
GetIndexToolInAvailableToolList( ToolSearchParameters.AvailableToolList, TOOLS[nBestToolIndex].sName) then
nBestToolIndex = i
dBestToolResidualDepth = dCurrentResidualDepth
sBestBladeEngagement = sCurrentBladeEngagement
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
end
-- entrambi incompleti
elseif dBestToolResidualDepth > 10 * GEO.EPS_SMALL and dCurrentResidualDepth > 10 * GEO.EPS_SMALL then
@@ -604,6 +612,7 @@ function MachiningLib.FindBlade( Proc, ToolSearchParameters)
if dCurrentResidualDepth > dBestToolResidualDepth then
nBestToolIndex = i
dBestToolResidualDepth = dCurrentResidualDepth
sBestBladeEngagement = sCurrentBladeEngagement
end
end
end
@@ -613,6 +622,7 @@ function MachiningLib.FindBlade( Proc, ToolSearchParameters)
ToolInfo.nToolIndex = nBestToolIndex
ToolInfo.dResidualDepth = dBestToolResidualDepth
ToolInfo.sBladeEngagement = sBestBladeEngagement
return ToolInfo
end
+1
View File
@@ -119,6 +119,7 @@ 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)
+42 -19
View File
@@ -204,9 +204,14 @@ local function CompareEdgesNoPreference( EdgeA, EdgeB)
end
local function GetEdgeToMachine( Edges, 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,23 +223,23 @@ local function GetEdgeToMachine( Edges, 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]
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
@@ -357,24 +362,44 @@ 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, 'Top', bAllowFastCuts),
Bottom = GetEdgeToMachine( FaceToMachine.Edges, 'Bottom', bAllowFastCuts),
TopGuillotine = GetEdgeToMachine( FaceToMachine.Edges, '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 = {
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 lato "veloce" (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)
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.IsFaceRectangle( FaceToMachine) then
local nToolIndexGuillotine
@@ -384,7 +409,7 @@ local function GetSingleCutStrategy( Proc, Part, OptionalParameters)
bAllowTopHead = true,
bAllowBottomHead = false,
FaceToMachine = FaceToMachine,
EdgeToMachine = EdgeToMachineList.Top,
EdgeToMachine = EdgeToMachineList.TopGuillotine,
Part = Part
})
nToolIndexGuillotine = ToolInfo.nToolIndex
@@ -590,7 +615,7 @@ local function CutWholeWaste( Proc, Part, OptionalParameters)
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
-- TODO valutare se deve funzionare solo per i rettangoli
elseif FaceData.IsFaceParallelogram( Proc.Faces[1]) then
local CuttingParametersList
@@ -798,9 +823,6 @@ 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}
-- in generale sta sollevato di pochissimo
local dExtraCut = -0.1
-- se tagli paralleli
@@ -819,9 +841,10 @@ local function CutWithDicing( Proc, Part, OptionalParameters)
end
end
end
local Cutting = {}
local ProcTrimesh = FeatureLib.GetProcFromTrimesh( vCuts[i][j], Part)
local _, Edges = FaceData.GetEdgesInfo( vCuts[i][j], 0)
local EdgeToMachine = BeamLib.FindEdgeBestOrientedAsDirection( Edges, vtToolDirection)
local FaceToMachine = ProcTrimesh.Faces[1]
local EdgeToMachine = BeamLib.FindEdgeBestOrientedAsDirection( FaceToMachine.Edges, vtToolDirection)
local dDepthToMachine = EdgeToMachine.dElevation + dExtraCut
local OptionalParametersFaceByBlade = {
dDepthToMachine = dDepthToMachine,
+24 -19
View File
@@ -343,6 +343,12 @@ function FACEBYBLADE.Make( Proc, Part, FaceToMachine, EdgeToMachine, OptionalPar
Cutting.bInvert = false
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
@@ -372,11 +378,12 @@ function FACEBYBLADE.Make( Proc, Part, FaceToMachine, EdgeToMachine, OptionalPar
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)
-- il BladeEngagement non deve cambiare, altrimenti è inutile invertire la direzione
if ( sBladeEngagementOpposite == Cutting.sBladeEngagement)
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'
Cutting.sBladeEngagement = sBladeEngagementOpposite
end
end
@@ -422,8 +429,10 @@ function FACEBYBLADE.Make( Proc, Part, FaceToMachine, EdgeToMachine, OptionalPar
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.sEdgeUsage = 'Guillotine'
-- taglio ridotto
else
dDepthToMachine = Cutting.dDepthToMachine + Cutting.dMaxRadialOffset
@@ -432,17 +441,19 @@ function FACEBYBLADE.Make( Proc, Part, FaceToMachine, EdgeToMachine, OptionalPar
end
end
-- si ritesta la fattibilità del taglio con le nuove profondità
local EdgeToMachineForEngagement = EdgeToMachine
if OppositeToolDirectionMode == 'Enabled' then
EdgeToMachineForEngagement = EdgeToMachineOpposite
end
local bIsApplicable, sBladeEngagement = MachiningLib.GetBladeEngagement( FaceToMachine, EdgeToMachineForEngagement, Part, TOOLS[Cutting.nToolIndex], dDepthToMachine)
if bIsApplicable then
Cutting.sBladeEngagement = sBladeEngagement
else
Cutting.sEdgeUsage = 'Standard'
dDepthToMachine = Cutting.dDepthToMachine
-- 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 = 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)) then
Cutting.sEdgeUsage = 'Standard'
dDepthToMachine = Cutting.dDepthToMachine
end
end
-- offset radiale (cambia se taglio opposto)
@@ -453,12 +464,6 @@ function FACEBYBLADE.Make( Proc, Part, FaceToMachine, EdgeToMachine, OptionalPar
end
end
-- ToolInvert
if Cutting.sBladeEngagement == 'DownUp' then
Cutting.bToolInvert = true
Cutting.bInvert = not Cutting.bInvert
end
-- completamento
Cutting.dCompletionPercentage = ( 1 - Cutting.dResidualDepth / Cutting.dDepthToMachine) * 100