af643b1ba5
-modifiche e correzione bug che impedivano il funzionamento corretto di headcut e split
306 lines
13 KiB
Lua
306 lines
13 KiB
Lua
-- ProcessSplit.lua by Egaltech s.r.l. 2022/09/26
|
|
-- Gestione calcolo tagli di testa per Travi
|
|
-- 2022/05/31 Aggiunta gestione sezioni alte e larghe con taglio di tipo diceCut.
|
|
-- 2022/06/10 Per sezioni alte e larghe aggiunta gestione finitura in base a sovramateriale e a parametro Q05 dell' eventuale lavorazione sostituita.
|
|
-- 2022/08/18 Aggiunta gestione macchine con testa da sotto con lama da sotto disabilitata.
|
|
-- 2022/09/08 Migliorato verso di lavorazione in caso di DoubleCut
|
|
|
|
-- Tabella per definizione modulo
|
|
local ProcessHeadCut = {}
|
|
|
|
-- Include
|
|
require( 'EgtBase')
|
|
local BL = require( 'BeamLib')
|
|
local Fbs = require( 'FacesBySaw')
|
|
local Cut = require( 'ProcessCut')
|
|
local Pocket = require( 'FaceByPocket')
|
|
|
|
EgtOutLog( ' ProcessHeadCut started', 1)
|
|
|
|
-- Dati
|
|
local BD = require( 'BeamData')
|
|
local ML = require( 'MachiningLib')
|
|
|
|
---------------------------------------------------------------------
|
|
-- Riconoscimento della feature
|
|
function ProcessHeadCut.Identify( Proc)
|
|
return ( Proc.Grp == 1 and Proc.Prc == 340)
|
|
end
|
|
|
|
---------------------------------------------------------------------
|
|
-- verifica curva per smusso (-1=errore curva, 0=estrusione non va bene, 1=ok)
|
|
local function VerifyCurveForChamfer( AuxId)
|
|
if not AuxId then
|
|
return -2
|
|
end
|
|
if ( EgtGetType( AuxId) & GDB_FY.GEO_CURVE) == 0 then
|
|
return -1
|
|
end
|
|
local vtExtr = EgtCurveExtrusion( AuxId, GDB_RT.GLOB)
|
|
-- va bene solo se direzione estrusione orizzontale
|
|
if abs( vtExtr:getZ()) > 0.1 then
|
|
return 0
|
|
end
|
|
return 1
|
|
end
|
|
|
|
---------------------------------------------------------------------
|
|
-- lavorazione smussi
|
|
local function MakeChamfer( nOriId, Proc, nPhase, nRawId, nPartId, dOvmHead)
|
|
-- verifico che lo smusso sia richiesto
|
|
local dDepth = EgtGetInfo( nOriId, 'Q06', 'd') or 0
|
|
if dDepth < 0.1 then return true end
|
|
-- ingombro del grezzo
|
|
local b3Raw = EgtGetRawPartBBox( nRawId)
|
|
-- recupero e verifico le entità curva associate (max 2)
|
|
local sVal = EgtGetInfo( nOriId, 'AUXID')
|
|
local vsAuxId = EgtSplitString( sVal)
|
|
local AuxId, Aux2Id
|
|
if vsAuxId and #vsAuxId >=1 then
|
|
AuxId = tonumber( vsAuxId[1])
|
|
end
|
|
if vsAuxId and #vsAuxId >=2 then
|
|
Aux2Id = tonumber( vsAuxId[2])
|
|
end
|
|
if AuxId then AuxId = AuxId + nOriId end
|
|
if Aux2Id then Aux2Id = Aux2Id + nOriId end
|
|
local nRes = VerifyCurveForChamfer( AuxId)
|
|
if nRes == 0 and Aux2Id then
|
|
AuxId = Aux2Id
|
|
nRes = VerifyCurveForChamfer( AuxId)
|
|
end
|
|
if nRes == -2 then
|
|
return true
|
|
end
|
|
if nRes == -1 then
|
|
local sErr = 'Error : missing profile geometry'
|
|
EgtOutLog( sErr)
|
|
return false, sErr
|
|
end
|
|
if nRes == 0 then
|
|
local sWarn = 'Warning : skipped not horizontal chamfer'
|
|
EgtOutLog( sWarn)
|
|
return true
|
|
end
|
|
-- recupero i dati della curva e del profilo
|
|
local dWidth = abs( EgtCurveThickness( AuxId))
|
|
local vtExtr = EgtCurveExtrusion( AuxId, GDB_RT.GLOB)
|
|
-- eseguo lo smusso solo se feature larga come la trave
|
|
if dWidth < b3Raw:getDimY() - 1 then
|
|
local sWarn = 'Warning : skipped chamfer (feature smaller than beam)'
|
|
EgtOutLog( sWarn)
|
|
return true, sWarn
|
|
end
|
|
local dExtra = 2
|
|
-- recupero la lavorazione
|
|
local sMilling = ML.FindMilling( 'Mark')
|
|
if not sMilling then
|
|
local sErr = 'Error : milling not found in library'
|
|
EgtOutLog( sErr)
|
|
return false, sErr
|
|
end
|
|
-- Inserisco la lavorazione del lato standard
|
|
local sName1 = 'SJN_' .. ( EgtGetName( Proc.Id) or tostring( Proc.Id))
|
|
local nMch1Id = EgtAddMachining( sName1, sMilling)
|
|
if not nMch1Id then
|
|
local sErr = 'Error adding machining ' .. sName1 .. '-' .. sMilling
|
|
EgtOutLog( sErr)
|
|
return false, sErr
|
|
end
|
|
-- aggiungo geometria
|
|
EgtSetMachiningGeometry( {{ AuxId, -1}})
|
|
-- assegno affondamento e offset radiale
|
|
EgtSetMachiningParam( MCH_MP.DEPTH, dDepth + dExtra)
|
|
EgtSetMachiningParam( MCH_MP.OFFSR, dExtra)
|
|
-- assegno lato di lavoro
|
|
EgtSetMachiningParam( MCH_MP.WORKSIDE, MCH_MILL_WS.RIGHT)
|
|
-- eseguo
|
|
if not ML.ApplyMachining( true, false) then
|
|
local _, sErr = EgtGetLastMachMgrError()
|
|
EgtSetOperationMode( nMchId, false)
|
|
return false, sErr
|
|
end
|
|
-- Inserisco la lavorazione del lato opposto
|
|
local sName2 = 'SJN_' .. ( EgtGetName( Proc.Id) or tostring( Proc.Id))
|
|
local nMch2Id = EgtAddMachining( sName2, sMilling)
|
|
if not nMch2Id then
|
|
local sErr = 'Error adding machining ' .. sName2 .. '-' .. sMilling
|
|
EgtOutLog( sErr)
|
|
return false, sErr
|
|
end
|
|
-- aggiungo geometria
|
|
EgtSetMachiningGeometry( {{ AuxId, -1}})
|
|
-- inverto direzione utensile
|
|
EgtSetMachiningParam( MCH_MP.TOOLINVERT, true)
|
|
-- assegno affondamento e offset radiale
|
|
EgtSetMachiningParam( MCH_MP.DEPTH, dDepth + dExtra)
|
|
EgtSetMachiningParam( MCH_MP.OFFSR, dExtra)
|
|
-- assegno lato di lavoro
|
|
EgtSetMachiningParam( MCH_MP.WORKSIDE, MCH_MILL_WS.LEFT)
|
|
-- eseguo
|
|
if not ML.ApplyMachining( true, false) then
|
|
local _, sErr = EgtGetLastMachMgrError()
|
|
EgtSetOperationMode( nMchId, false)
|
|
return false, sErr
|
|
end
|
|
return true, nil
|
|
end
|
|
|
|
---------------------------------------------------------------------
|
|
-- Applicazione della lavorazione
|
|
function ProcessHeadCut.Make( Proc, nPhase, nRawId, nPartId, dOvmHead, bNeedHCut)
|
|
-- ingombro del grezzo
|
|
local b3Raw = EgtGetRawPartBBox( nRawId)
|
|
-- inserimento smussi
|
|
local nOriId = EgtGetInfo( Proc.Id, 'ORI', 'i')
|
|
if nOriId then
|
|
local bOkc, sErrC = MakeChamfer( nOriId, Proc, nPhase, nRawId, nPartId, dOvmHead)
|
|
if not bOkc then return bOkc, sErrC end
|
|
end
|
|
-- recupero la lavorazione
|
|
local sCutting = ML.FindCutting( 'HeadSide')
|
|
if not sCutting then
|
|
local sErr = 'Error : cutting not found in library'
|
|
EgtOutLog( sErr)
|
|
return false, sErr
|
|
end
|
|
-- recupero i dati dell'utensile
|
|
local dSawDiam = 400
|
|
local dMaxDepth = 50
|
|
if EgtMdbSetCurrMachining( sCutting) then
|
|
local sTuuid = EgtMdbGetCurrMachiningParam( MCH_MP.TUUID)
|
|
if EgtTdbSetCurrTool( EgtTdbGetToolFromUUID( sTuuid) or '') then
|
|
dSawDiam = EgtTdbGetCurrToolParam( MCH_TP.DIAM) or dSawDiam
|
|
dMaxDepth = EgtTdbGetCurrToolMaxDepth() or dMaxDepth
|
|
end
|
|
end
|
|
local dMaxVertDepth = dMaxDepth - ( BD.DECR_VERT_CUT or 0)
|
|
-- recupero la eventuale lavorazione con lama da sotto
|
|
local sCutting2 = ML.FindCutting( 'HeadSide_H2', false, true)
|
|
-- recupero i dati della eventuale seconda lama
|
|
local dSawDiam2 = 0
|
|
local dMaxDepth2 = 0
|
|
if sCutting2 and EgtMdbSetCurrMachining( sCutting2) then
|
|
local sTuuid2 = EgtMdbGetCurrMachiningParam( MCH_MP.TUUID)
|
|
if EgtTdbSetCurrTool( EgtTdbGetToolFromUUID( sTuuid2) or '') then
|
|
dSawDiam2 = EgtTdbGetCurrToolParam( MCH_TP.DIAM) or dSawDiam2
|
|
dMaxDepth2 = EgtTdbGetCurrToolMaxDepth() or dMaxDepth2
|
|
end
|
|
end
|
|
-- caratteristiche taglio
|
|
local dDimYRef = EgtIf( b3Raw:getDimZ() < BD.MIN_DIM_HBEAM + 10 * GEO.EPS_SMALL, dMaxDepth, abs( BD.MAX_DIM_HTCUT_HBEAM))
|
|
local bBigSectionCut = ( b3Raw:getDimY() > 2 * dDimYRef - BD.CUT_EXTRA_MIN + 10 * GEO.EPS_SMALL) and
|
|
( b3Raw:getDimZ() > EgtIf( BD.TURN, 2 * dMaxVertDepth, dMaxVertDepth + dMaxDepth2) - 2 * BD.CUT_EXTRA_MIN + 10 * GEO.EPS_SMALL)
|
|
local bHorizCut = ( not bBigSectionCut and ( b3Raw:getDimY() > b3Raw:getDimZ() + 10 * GEO.EPS_SMALL or BD.TURN) and b3Raw:getDimZ() < dMaxVertDepth - BD.CUT_EXTRA)
|
|
local bDoubleHorizCut = ( ( BD.DOWN_HEAD or BD.TURN) and not bBigSectionCut and not bHorizCut and b3Raw:getDimY() > 2 * dDimYRef - BD.CUT_EXTRA_MIN + 10 * GEO.EPS_SMALL)
|
|
local bDoubleCut = ( not bBigSectionCut and not bHorizCut and not bDoubleHorizCut and b3Raw:getDimY() > dDimYRef - BD.CUT_EXTRA + 10 * GEO.EPS_SMALL)
|
|
-- dati geometrici del taglio
|
|
local ptC, vtN = EgtSurfTmFacetCenter( Proc.Id, 0, GDB_ID.ROOT)
|
|
-- se non obbligatorio e coincide con inizio grezzo, non va fatto
|
|
if not bNeedHCut and AreSameVectorApprox( vtN, X_AX()) and abs( ptC:getX() - b3Raw:getMax():getX()) < 10 * GEO.EPS_SMALL then
|
|
return true
|
|
end
|
|
-- determino se più tagli con offset
|
|
local nCuts = max( ceil( dOvmHead / ( BD.MAX_LEN_SCRAP_START or BD.MAX_LEN_SCRAP)), 1)
|
|
local dOffsL = dOvmHead / nCuts
|
|
-- se taglio per sezioni alte e larghe
|
|
if bBigSectionCut then
|
|
if dOvmHead > 0 then
|
|
local nQ05 = EgtGetInfo( nOriId or GDB_ID.NULL, 'Q05', 'i') or 0
|
|
-- se finitura con lama
|
|
if nQ05 == 1 or nQ05 == 0 then
|
|
local bOk, sErr = Cut.Make( Proc, nPhase, nRawId, nPartId, dOvmHead, nil, false, true, nil, nil, dCurrOvmT)
|
|
if not bOk then return bOk, sErr end
|
|
-- se finitura con truciolatore
|
|
elseif nQ05 == 2 then
|
|
local b3Solid = EgtGetBBoxGlob( EgtGetFirstNameInGroup( nPartId, 'Box') or GDB_ID.NULL, GDB_BB.STANDARD)
|
|
if not b3Solid then
|
|
local sErr = 'Error : part box not found'
|
|
EgtOutLog( sErr)
|
|
return false, sErr
|
|
end
|
|
local sPocketing = ML.FindPocketing( 'OpenPocket', nil, 0)
|
|
if not sPocketing then
|
|
local sErr = 'Error : pocketing not found in library'
|
|
EgtOutLog( sErr)
|
|
return false, sErr
|
|
end
|
|
local bOk, sErr = Pocket.Make( Proc, Proc.Id, 0, sPocketing, nPartId, b3Solid)
|
|
if not bOk then return bOk, sErr end
|
|
end
|
|
end
|
|
-- se tagli standard
|
|
elseif not bDoubleHorizCut then
|
|
-- flag di lavorazione faccia
|
|
local nOrthoOpposite = EgtIf( bHorizCut, MCH_MILL_FU.ORTHO_DOWN, MCH_MILL_FU.ORTHO_FRONT)
|
|
-- calcolo extra taglio ed accorciamento
|
|
local dCutExtra = 0
|
|
local dAccStart = 0
|
|
local dAccEnd = 0
|
|
if b3Raw:getDimZ() < BD.MIN_DIM_HBEAM + 10 * GEO.EPS_SMALL or b3Raw:getDimY() < 2 * BD.MAX_DIM_HTCUT_HBEAM + 10 * GEO.EPS_SMALL then
|
|
dCutExtra = EgtIf( bDoubleCut, - 0.5 * b3Raw:getDimY() + BD.CUT_EXTRA_MIN, BD.CUT_EXTRA)
|
|
else
|
|
dCutExtra = - ( b3Raw:getDimY() - dMaxDepth)
|
|
local dSawRad = dSawDiam / 2
|
|
local dKL = dSawRad - dMaxDepth + b3Raw:getDimY() / 2 + BD.CUT_EXTRA_MIN
|
|
if BD.C_SIMM then
|
|
dAccEnd = sqrt( dSawRad * dSawRad - dKL * dKL)
|
|
else
|
|
dAccStart = sqrt( dSawRad * dSawRad - dKL * dKL)
|
|
end
|
|
end
|
|
-- se necessari tagli in doppio, eseguo gli opposti
|
|
if bDoubleCut then
|
|
for i = nCuts, 1, -1 do
|
|
local dCutOffset = ( i - 1) * dOffsL
|
|
local bOk, sErr = Fbs.MakeOne( Proc.Id, 0, sCutting, dSawDiam, MCH_MILL_FU.ORTHO_BACK, nil, dCutExtra, BD.CUT_SIC, dCutOffset, dAccStart, dAccEnd, '', b3Raw, true)
|
|
if not bOk then return false, sErr end
|
|
end
|
|
end
|
|
-- eseguo i tagli necessari
|
|
for i = nCuts, 1, -1 do
|
|
local dCutOffset = ( i - 1) * dOffsL
|
|
local bOk, sErr = Fbs.MakeOne( Proc.Id, 0, sCutting, dSawDiam, nOrthoOpposite, nil, dCutExtra, BD.CUT_SIC, dCutOffset, dAccStart, dAccEnd, '', b3Raw)
|
|
if not bOk then return false, sErr end
|
|
end
|
|
-- altrimenti necessari tagli da sopra e sotto con testa opportuna
|
|
else
|
|
-- verifico esistenza della lavorazione con lama da sotto
|
|
if not sCutting2 then
|
|
local sErr = 'Error : cutting H2 not found in library'
|
|
EgtOutLog( sErr)
|
|
return false, sErr
|
|
end
|
|
-- verifico che le due lame riescano a lavorare la sezione
|
|
local dDimZ = b3Raw:getDimZ()
|
|
local dExtra = dMaxVertDepth + dMaxDepth2 - dDimZ
|
|
if dExtra - 2 * BD.CUT_EXTRA_MIN + 10 * GEO.EPS_SMALL < 0 then
|
|
local sErr = 'Error : section too big for head cut'
|
|
EgtOutLog( sErr)
|
|
return false, sErr
|
|
end
|
|
-- calcolo extra taglio ed accorciamento
|
|
local dCutExtra = -dMaxDepth2 + dExtra / 2 + BD.CUT_EXTRA_MIN
|
|
local dCutExtra2 = -dMaxVertDepth + dExtra / 2 + BD.CUT_EXTRA_MIN
|
|
local dAccStart = 0
|
|
local dVzLimDwnUp
|
|
if BD.TURN then dVzLimDwnUp = -2 end
|
|
-- eseguo i tagli da sotto necessari
|
|
for i = nCuts, 1, -1 do
|
|
local dCutOffset = ( i - 1) * dOffsL
|
|
local bOk, sErr = Fbs.MakeOne( Proc.Id, 0, sCutting2, dSawDiam2, MCH_MILL_FU.ORTHO_TOP, dVzLimDwnUp, dCutExtra2, BD.CUT_SIC, dCutOffset, dAccStart, 0, '', b3Raw)
|
|
if not bOk then return false, sErr end
|
|
end
|
|
-- eseguo i tagli da sopra necessari
|
|
for i = nCuts, 1, -1 do
|
|
local dCutOffset = ( i - 1) * dOffsL
|
|
local bOk, sErr = Fbs.MakeOne( Proc.Id, 0, sCutting, dSawDiam, MCH_MILL_FU.ORTHO_DOWN, dVzLimDwnUp, dCutExtra, BD.CUT_SIC, dCutOffset, dAccStart, 0, '', b3Raw)
|
|
if not bOk then return false, sErr end
|
|
end
|
|
end
|
|
return true
|
|
end
|
|
|
|
---------------------------------------------------------------------
|
|
return ProcessHeadCut
|