diff --git a/TemplateTool.lua b/TemplateTool.lua new file mode 100644 index 0000000..46d1d64 --- /dev/null +++ b/TemplateTool.lua @@ -0,0 +1,700 @@ +-- 2024/11/22 +-- Template per la creazione di un cabinet + +-- Intestazioni +require( 'EgtBase') +_ENV = EgtProtectGlobal() +EgtEnableDebug( false) + +------------------------------------------------------------------------------------------------------------------------- +-- FUNZIONI BASE PER GENERARE I COMPO SOLID INIZIO +------------------------------------------------------------------------------------------------------------------------- + +local TOOL = {} + +_G.TOOL = TOOL + +function TOOL.SaveMePlease() + EgtSaveFile('D:\\Temp\\marmo\\Vein3D\\FUCK.nge') +end + +-- CREAZIONE dei Layer di un singolo Part +-- I nomi dei layer sono: OutLoop, Region, Ref, Labels, Aux +function TOOL.CreatePartLayer(PartName, sUNICode) + -- Pezzo e Layer + local Pz = EgtGroup(GDB_ID.ROOT,GDB_RT.LOC) -- pezzo + EgtSetName( Pz, sUNICode..PartName) + local LOut = EgtGroup(Pz,GDB_RT.LOC) -- layer della figura principale + EgtSetName(LOut,'OutLoop') + local LReg = EgtGroup(Pz,GDB_RT.LOC) -- layer regione + EgtSetName(LReg,'Region') + local LRef = EgtGroup(Pz,GDB_RT.LOC) -- layer riferimenti + EgtSetName(LRef,'Ref') + EgtSetStatus( LRef, GDB_ST.OFF) + local LLabel= EgtGroup(Pz,GDB_RT.LOC) -- layer etichette + EgtSetName(LLabel,'Labels') + local LAux= EgtGroup(Pz,GDB_RT.LOC) -- layer etichette + EgtSetName(LAux,'Aux') + EgtOutLog(' Creo Part: '..sUNICode..PartName) + --SaveMePlease() + return Pz +end +-- + +-- RESTITUISCE una tabella con gli Id dei layer costruiti nella funzione CreatePartLayer part, +-- Se il nome del Part non esiste restituice nil +function TOOL.FindLayers( IdPart) + if not EgtIsPart( IdPart) then + CMP.ERR = 1 + CMP.MSG = CMP.MSG.." In FindLayers 'IdPart' non è un Part" + return nil + end + local tbLayer = {} + tbLayer['OutLoop'] = EgtGetFirstNameInGroup(IdPart, 'OutLoop') + tbLayer['Region'] = EgtGetFirstNameInGroup(IdPart, 'Region') + tbLayer['Ref'] = EgtGetFirstNameInGroup(IdPart, 'Ref') + tbLayer['Labels'] = EgtGetFirstNameInGroup(IdPart, 'Labels') + tbLayer['Aux'] = EgtGetFirstNameInGroup(IdPart, 'Aux') + local nInLoopLay = EgtGetFirstNameInGroup(IdPart, 'InLoop') + if nInLoopLay then + tbLayer['InLoop'] = nInLoopLay + end + return tbLayer +end +-- + +-- ASSEGNO Info per conoscere le direzioni dei lati +function TOOL.SetMachiningInfo(Layer, bInLoop) + -- if not bInLoop then return end + if EgtIsLayer( Layer) then + local LayerName = EgtGetName( Layer) + -- verifico che sia di tipo In o Out, altrimenti ricerco nel Part il layer + if not LayerName == 'OutLoop' or not LayerName == 'InLoop' then + Layer = EgtGetFirstInGroup( Layer) + CMP.ERR = 2 + CMP.MSG = CMP.MSG.." In SetMachiningInfo il Layer non è di tipo 'OutLoop' o 'InLoop'." + end + else + CMP.ERR = 3 + CMP.MSG = CMP.MSG.." In SetMachiningInfo il Layer non è di tipo 'OutLoop' o 'InLoop'." + end + local nId = EgtGetFirstInGroup(Layer) + local nPrevId = EgtGetLastInGroup(Layer) + local nNextId = EgtGetNext(nId) + local nFirstId = nId + local nEdges = EgtGetGroupObjs(Layer) + if nEdges == 1 then + EgtSetInfo(nId, 'PrevAng', 0) + EgtSetInfo(nId, 'NextAng', 0) + return + end + for i = 1, nEdges do + -- recupero i dati + local vtCurrS = EgtSV(nId, GDB_RT.GLOB) + local vtPrevE = EgtEV(nPrevId, GDB_RT.GLOB) + local vtCurrE = EgtEV(nId, GDB_RT.GLOB) + local vtNextS = EgtSV(nNextId, GDB_RT.GLOB) + local vtAx = Z_AX() + if bInLoop then vtAx=-vtAx end + local NextAng = GetRotation( vtCurrE, vtNextS, vtAx) + local PrevAng = GetRotation( vtPrevE, vtCurrS, vtAx) + -- scrivo le info + EgtSetInfo(nId, 'PrevAng', PrevAng) + EgtSetInfo(nId, 'NextAng', NextAng) + -- aggiorno gli id + nPrevId = nId + nId = nNextId + nNextId = EgtGetNext(nNextId) + if nNextId == nil then + nNextId = nFirstId + end + end +end +-- + +-- DEVO RICEVERE SOLO UN CONTORNO!! Da semplificare +-- Dato un contorno ricavo i lati nel Layer di appartenenza del contorno +-- altrimenti se Part ricavo i lati nel loop specificato (Default=OutLoop o InLoop) +function TOOL.ExplodeAndNameEdges( IdLoop, bInLoop) + local sNameLayer = '' + if bInLoop == nil then bInLoop = false end + if bInLoop then + sNameLayer = 'InLoop' + else + sNameLayer = 'OutLoop' + end + if not IdLoop or IdLoop == -1 then end + -- Se l'Id è un Part + if EgtIsPart( IdLoop) then + local tbLayer = TOOL.FindLayers( IdLoop) + if tbLayer then IdLoop = EgtGetFirstInGroup( tbLayer[sNameLayer]) end + end + -- Se l'Id è un Layer + if EgtIsLayer( IdLoop) then + local LayerName = EgtGetName( IdLoop) + -- verifico che sia di tipo In o Out, altrimenti ricerco nel Part il layer + if LayerName == sNameLayer then + IdLoop = EgtGetFirstInGroup( IdLoop) + else + local tbLayer = TOOL.FindLayers( EgtGetParent(IdLoop)) + if tbLayer then IdLoop = EgtGetFirstInGroup( tbLayer[sNameLayer]) end + end + end + local nLay = EgtGetParent(IdLoop) + local nEdge, nTotEdges = EgtExplodeCurveCompo(IdLoop) + local nCount = 1 + local tbIdLoop = {} + while nEdge do + local tbName = EgtNumToString(nCount) + EgtSetName( nEdge, "A"..tbName) + nCount = nCount + 1 + table.insert( tbIdLoop, nEdge) + nEdge = EgtGetNext(nEdge) + end + -- Ricavo info direzioni + TOOL.SetMachiningInfo(nLay,bInLoop) + return tbIdLoop +end +-- + +-- CREAZIONE LAyer per le dimensioni +function TOOL.CreateDimensionLayer() + local Pz = EgtGroup(GDB_ID.ROOT,GDB_RT.LOC) -- layer dimensioni e etichette + EgtSetName( Pz, 'Dimensions') +end +-- + +-- Per disporre i pezzi in piano non sovrappposti (in assemblaggio non serve) +local HorizontalOffset = 0 + +-- Creazione del part assegnato un contorno esploso: +-- tbLayer : tabella dei layer (FindLayers dato il Part) +-- sName : nome da assegnare in grafica +-- tbIdEntCrv: tabella delle entità che costituiscono il contorno (da ExplodeAndNameEdges) +-- dTh : spessore pezzo +-- dOffset : per messa in piano dei pezzi (0 se non si usa) +-- bInLoop : tipo di contorno +function TOOL.CreatePart(tbLayer, sName, tbIdEntCrv, dTh, bInLoop) + -- recupero il layer del contorno + local IdCurrLayer = EgtGetParent( tbIdEntCrv[1]) + -- recupero l'Id del part + local IdPart = EgtGetParent( IdCurrLayer) + -- costruisco il contorno chiuso + local IdLoop = EgtCurveCompoByChain( IdCurrLayer, tbIdEntCrv, EgtSP(tbIdEntCrv[1],GDB_RT.GLOB), false, GDB_RT.GLOB) + -- Nel Layer Region definisco la regione piana + local IdReg = EgtSurfFlatRegion(tbLayer['Region'],IdLoop) + -- Se InLoop allora faccio la sottrazione con la regione OutRegion + if bInLoop then + local IdOutRegion = EgtGetPrev(IdReg) + local vtNorm1 = EgtSurfFrNormVersor(IdOutRegion) + local vtNorm2 = EgtSurfFrNormVersor(IdReg) + if AreOppositeVectorApprox( vtNorm1, vtNorm2) then + EgtInvertSurf(IdReg) + end + if not EgtSurfFrSubtract( IdOutRegion,IdReg) then + CMP.ERR = 5 + CMP.MSG = CMP.MSG.." Sottrazione tra superficie 'OutLoop' "..tostring(IdOutRegion).." e 'InLoop' "..tostring(IdReg).." non riuscita." + end + EgtErase(IdReg) + end + -- if bInLoop then EgtInvertCurve(IdLoop) end + -- elimino il contorno chiuso + EgtErase(IdLoop) + + -- Se sono InLoop non devo settare + if bInLoop then + for i = 1, #tbIdEntCrv do + EgtInvertCurve(tbIdEntCrv[i]) + end + return + end + -- definisco spessore pezzo + EgtSetInfo(IdPart, 'Th', dTh) + -- INFO NECESSARIA + EgtSetInfo(IdPart, 'Paired',tostring(IdPart)) + + -- inserisco le etichette del pezzo nel centro della superofocie + local ptTop = EgtCP( IdReg, GDB_RT.GLOB) + local ptBottom = Point3d( ptTop:getX(), -ptTop:getY(), dTh) + EgtTextAdv(tbLayer['Labels'], ptTop,0,sName, '', 10, '', 15,1.5,0,GDB_TI.MC) + if CMP.DrawSolid then + EgtSetGridFrame(Frame3d(ORIG(),GDB_FR.BOTTOM)) + EgtTextAdv(tbLayer['Labels'], ptBottom,0,sName, '', 10, '', 15,1.5,0,GDB_TI.MC, GDB_RT.GRID) + EgtSetGridFrame(Frame3d(ORIG(),GDB_FR.TOP)) + end + -- dispongo il pezzo in piano + local vtMove = Vector3d({HorizontalOffset,0,0}) + --EgtMove(IdPart,vtMove, GDB_RT.GLOB) + HorizontalOffset = HorizontalOffset + ptTop:getX() + 10 +end +-- + +-- Sposto l'etichetta del nome del Part nel Solido associato +function TOOL.RelocateLabels() + local nPartId = EgtGetFirstPart() + while nPartId do + local nChild = EgtGetInfo(nPartId, 'Child','i') + if nChild then + local nLaySource = EgtGetFirstNameInGroup(nPartId, 'Labels') + if nLaySource then EgtRelocateGlob( nLaySource, nChild) end + end + nPartId = EgtGetNext(nPartId) + end +end +-- + +-- Crea una copia dello spigolo e lo salva nel layer Ref +-- Nome del part (da tbName[1]), +-- Nome del Layer (OutLoop o InLoop), +-- Nome dello spigolo, +-- Nome della copia riferimento +-- Info per spostamento Ref in funzione di una variabile +function TOOL.CreateReference( sUNICode, sNamePart, sNameLayer,sNameEdge, sNameRef, dVar, sDir) + local IdPart = EgtGetFirstNameInGroup(GDB_ID.ROOT, sUNICode..sNamePart) + local tbLayer = TOOL.FindLayers( IdPart) + --accoppiamento di left su bottom + local IdEnt = EgtGetFirstNameInGroup(tbLayer[sNameLayer], sNameEdge) + if not IdEnt then + CMP.ERR=6 + CMP.MSG= CMP.MSG..' Non esiste il lato '..sNameEdge..' nel layer '..sNameLayer..' del part '..sNamePart + return + end + -- creo la copia dello spigolo come riferimento + local IdRef = EgtCopy( IdEnt, tbLayer['Ref']) + EgtSetName( IdRef, sNameRef) + if dVar and sDir then + EgtSetInfo(IdRef, 'Var', dVar) + EgtSetInfo(IdRef, 'Dir', sDir) + end + return IdRef +end +-- + +-- Crea una copia dello del punto dello spigolo e lo salva nel layer Ref +-- Nome del part (da tbName[1]), +-- Nome del Layer (OutLoop o InLoop), +-- Nome dello spigolo, +-- Nome della copia punto +-- Tipo di punto: 0/nil START, 1 END, 2 MID +function TOOL.CreatePointReference( sNamePart, sNameLayer,sNameEdge, sNameRef, nTypePt) + local IdPart = EgtGetFirstNameInGroup(GDB_ID.ROOT, sUNICode..sNamePart) + local tbLayer = TOOL.FindLayers( IdPart) + --accoppiamento di left su bottom + local IdEnt = EgtGetFirstNameInGroup(tbLayer[sNameLayer], sNameEdge) + if not IdEnt then + CMP.ERR=6 + CMP.MSG= CMP.MSG..' Non esiste il lato '..sNameEdge..' nel layer '..sNameLayer..' del part '..sNamePart + return + end + local pt = EgtSP(IdEnt, GDB_RT.GLOB) + if nTypePt == 1 then + pt = EgtEP(IdEnt, GDB_RT.GLOB) + elseif nTypePt == 2 then + pt = EgtMP(IdEnt, GDB_RT.GLOB) + end + local IdPtRef = EgtPoint( tbLayer['Ref'], pt, GDB_RT.GLOB) + EgtSetName(IdPtRef, sNameRef) + return IdPtRef +end +-- + +-- Accoppia lato a riferimento +-- Nome del pezzo da accoppiare +-- Nome del riferimento da usare +-- Nome del pezzo destinatario dell'accoppiamento +-- Nome del riferimento da usare come destinatario dell'accoppiamento +-- Concordanza del verso dei due spigoli +-- Angolo relativo tra i due pezzi: porta la normale della regione del pezzo corrente a coincidere +-- con la normale della regione del pezzo destinatario; il segno è riferito al verso del riferimento del part destinatario +-- Modalità di accoppiamento tra gli spigoli (0: start-start, 1:start-end, 2: end-start, 3: end-end, 4: mid-mid) +function TOOL.SetPairInfo( sUNICode, sMyNamePart, sNameMyRef, sToNamePart, sNameToRef, nPairSpin, dPairAng, nPairMode) + local nPart = EgtGetFirstNameInGroup(GDB_ID.ROOT, sUNICode..sMyNamePart) + EgtSetInfo(nPart, "PairMyRef", sNameMyRef) + EgtSetInfo(nPart, "PairToRef", sUNICode..sToNamePart.."_"..sNameToRef) + EgtSetInfo(nPart, "PairSpin", nPairSpin) + EgtSetInfo(nPart, "PairAng", dPairAng) + if nPairMode then EgtSetInfo(nPart, "PairMode", nPairMode) end +end + +-- Disegna la quota lineare +-- Nome del part in cui trovare il primo punto di riferimento +-- Nome del punto riferimento nel part indicato sopra +-- Nome del part in cui trovare il secondo punto di riferimento +-- Nome del punto riferimento nel part indicato sopra +-- Nome/valore stringa da scrivere nella dimensione +-- Frame del piano su cui disegnare la quotatura +-- Offset etichetta rispetto al punto medio +local function DrawLinearDimension( sNamePart1, sNameRef1, sNamePart2, sNameRef2, sNameDimension, GridFrame, ptOffset) + EgtSetGridFrame(GridFrame) + local nDimLay = EgtGetFirstNameInGroup(GDB_ID.ROOT, 'Dimensions') + local nBottomLay = EgtGetFirstNameInGroup(GDB_ID.ROOT, sUNICode..sNamePart1) + local nRefBottom = EgtGetFirstNameInGroup(nBottomLay, 'Ref') + local nRef = EgtGetFirstNameInGroup(nRefBottom, sNameRef1) + local pt1 = EgtSP( nRef, GDB_RT.GRID) + local nTopLay = EgtGetFirstNameInGroup(GDB_ID.ROOT, sUNICode..sNamePart2) + local nRefTop = EgtGetFirstNameInGroup(nTopLay, 'Ref') + nRef = EgtGetFirstNameInGroup(nRefTop, sNameRef2) + local pt2 = EgtSP( nRef, GDB_RT.GRID) + local ptMid = (pt1 + pt2) / 2 + ptOffset + local nDim = EgtAlignedDimension( nDimLay, pt1, pt2, ptMid, sNameDimension, GDB_RT.GRID) + EgtSetColor( nDim, EgtStdColor( 'YELLOW')) + EgtRelocate(nDim, GDB_RT.GRID) + EgtSetName(nDim, sNameDimension) +end +-- +------------------------------------------------------------------------------------------------------------------------- +-- FUNZIONI BASE PER GENERARE I COMPO SOLID FINE +------------------------------------------------------------------------------------------------------------------------- + +-- ------------------------------------------------------------------------------------------------------------------------- +-- -- CREAZIONE/IMPORTAZIONE Loop INIZIO +-- ------------------------------------------------------------------------------------------------------------------------- +-- -- Importa un contorno chiuso da file nge +-- function ImportOutLoop( tbLayer, sNameFileNGE) +-- local OutLayer = tbLayer['OutLoop'] +-- if not EgtInsertFile( sNameFileNGE) then +-- EgtOutLog(' IMPORTAZIONE FALLITA: '..sNameFileNGE) +-- end +-- -- recupero ultimo Part +-- local LastPart = EgtGetLastPart() +-- local FstLayerInLstPart = EgtGetFirstGroupInGroup( LastPart) +-- local IdLoop = EgtGetFirstInGroup( FstLayerInLstPart) +-- if not EgtRelocateGlob( IdLoop, OutLayer) then +-- EgtOutLog(' RELOCATE AFLLITA MISERAMENTE: '..tostring(IdLoop)..';'..tostring(OutLayer)) +-- end +-- EgtErase(LastPart) +-- local tbIdLoop = ExplodeAndNameEdges( IdLoop) + +-- EgtSetInfo(tbIdLoop[1],'AF',1) +-- EgtSetInfo(tbIdLoop[2],'AF',2) +-- EgtSetInfo(tbIdLoop[3],'AF',2) +-- EgtSetInfo(tbIdLoop[4],'AF',2) +-- EgtSetInfo(tbIdLoop[5],'AF',2) +-- EgtSetInfo(tbIdLoop[6],'AF',2) +-- EgtSetInfo(tbIdLoop[7],'AF',1) +-- --SaveMePlease() +-- -- definizione SideAng +-- -- EgtSetInfo( tbIdLoop[1], 'OrigSideAng', 45) +-- return tbIdLoop +-- end +-- -- + +-- -- Crea un contorno chiuso rettangolare come OutLoop (con diagonale da origine a ptEND) +-- function CreateWaterfall( tbLayer, sNameLayer, ptEND, PrevAng, NextAng, bIsPrevWaterfall, bIsNextWaterfall) +-- local OffseAng = 3 +-- local NAng = NextAng/2 + OffseAng +-- local PAng = PrevAng/2 + OffseAng +-- if not bIsNextWaterfall then +-- if NAng >= 0 then +-- NAng = -90 + NextAng +-- else +-- NAng = -90 - NextAng +-- end +-- end +-- if not bIsPrevWaterfall then +-- if PAng >= 0 then +-- PAng = -90 + PrevAng +-- else +-- PAng = -90 - PrevAng +-- end +-- end +-- local IdLoop = EgtRectangle2P(tbLayer[sNameLayer],{0,0,0}, ptEND,GDB_RT.GLOB) +-- local tbIdLoop = ExplodeAndNameEdges( IdLoop) +-- -- definizione SideAng +-- -- bla bla bla--------------------------------------------------------------------------------------------------- +-- EgtSetInfo( tbIdLoop[2], 'OrigSideAng', -NAng) +-- EgtSetInfo( tbIdLoop[2], 'SideAng', -NAng) +-- EgtSetInfo( tbIdLoop[4], 'OrigSideAng', -PAng) +-- EgtSetInfo( tbIdLoop[4], 'SideAng', -PAng) +-- -- bla bla bla--------------------------------------------------------------------------------------------------- +-- return tbIdLoop +-- end +-- -- +-- -- Crea un contorno chiuso rettangolare come OutLoop (con diagonale da origine a ptEND) +-- function CreateSplashtop( tbLayer, sNameLayer, ptEND, PrevAng, NextAng, bIsPrevSplashtop, bIsNextSplashtop) +-- local OffseAng = 3 +-- local NAng = NextAng/2 + OffseAng +-- local PAng = PrevAng/2 + OffseAng +-- if not bIsNextWaterfall then +-- if NAng >= 0 then +-- NAng = 90 - NextAng +-- else +-- NAng = 90 + NextAng +-- end +-- end +-- if not bIsPrevWaterfall then +-- if PAng >= 0 then +-- PAng = 90 - PrevAng +-- else +-- PAng = 90 + PrevAng +-- end +-- end +-- EgtOutLog(PAng) +-- EgtOutLog(NAng) +-- local IdLoop = EgtRectangle2P(tbLayer[sNameLayer],{0,0,0}, ptEND,GDB_RT.GLOB) +-- local tbIdLoop = ExplodeAndNameEdges( IdLoop) +-- -- definizione SideAng +-- -- bla bla bla--------------------------------------------------------------------------------------------------- +-- EgtSetInfo( tbIdLoop[2], 'OrigSideAng', -NAng) +-- EgtSetInfo( tbIdLoop[2], 'SideAng', -NAng) +-- EgtSetInfo( tbIdLoop[4], 'OrigSideAng', -PAng) +-- EgtSetInfo( tbIdLoop[4], 'SideAng', -PAng) +-- -- bla bla bla--------------------------------------------------------------------------------------------------- +-- return tbIdLoop, PAng, NAng +-- end +-- -- + +-- ------------------------------------------------------------------------------------------------------------------------- +-- -- CREAZIONE/IMPORTAZIONE Loop FINE +-- ------------------------------------------------------------------------------------------------------------------------- + +-- -- Restituisce l'angolo precedente e successivo dell'aentità passata +local function GetPrevNextAng(IdEnt) + local PrevAng = EgtGetInfo(IdEnt,'PrevAng','d') or 0 + local NextAng = EgtGetInfo(IdEnt,'NextAng','d') or 0 + return PrevAng, NextAng +end + +-- Confronto i dati del file.dat con quelli letti da programma +function IsDataChanged() + local bOk = false + if not tbOrigVal.v1 then return true end + if math.abs(CMP.V1 - tbOrigVal.v1) > 0.5 then bOk = bOk or true end + if math.abs(CMP.V2 - tbOrigVal.v2) > 0.5 then bOk = bOk or true end + if math.abs(CMP.V3 - tbOrigVal.v3) > 0.5 then bOk = bOk or true end + if math.abs(CMP.V4 - tbOrigVal.v4) > 0.5 then bOk = bOk or true end + if math.abs(CMP.V5 - tbOrigVal.v5) > 0.5 then bOk = bOk or true end + if math.abs(CMP.V6 - tbOrigVal.v6) > 0.5 then bOk = bOk or true end + if math.abs(CMP.V7 - tbOrigVal.v7) > 0.5 then bOk = bOk or true end + if math.abs(CMP.V8 - tbOrigVal.v8) > 0.5 then bOk = bOk or true end + return bOk +end + +function CalcDraftAngle( vtDir1, vtDir2, dPairAng1, dPairAng2, dAngBetween) + -- vengono restituiti il SideAng ( calcolato dall'angolo in 3d), i due nuovi angoli di forma per i due pezzi + -- dBeta1 è riferito al pezzo 1 e dBeta2 è riferito al pezzo 2 + local dAngTilt1 = dPairAng1 - 90 + local dAngTilt2 = dPairAng2 - 90 + local vtN1 = Vector3d({0,100,0}) + local vtN2 = Vector3d({0,100,0}) + vtN1:rotate(X_AX(),dAngTilt1) + vtN2:rotate(X_AX(), dAngTilt2) + vtN2:rotate(Z_AX(), dAngBetween) + local vtPerp = vtN1 ^ vtN2 + local vtInters1 = vtN1 ^ vtPerp + local vtInters2 = vtPerp ^ vtN2 + --local dAng3d = GetRotation(vtInters1, vtInters2, vtPerp) + local dAng3d = GetAngle(vtInters1, vtInters2) + local dBeta1 = GetAngle( vtDir1, vtPerp) + local dBeta2 = GetAngle( vtDir2, vtPerp) + local dSideAng = (180 - dAng3d) / 2 + return dSideAng, dBeta1, dBeta2 +end + +function TJunction(dAngBetween, dTh1, dTh2, nType, dLen1, dLen2, bOnLoop) + -- restituisce le lunghezze L1 e L2 adattate in base al tipo di giunzione + -- nType == 1 -> TrimStart ( del Part2) + -- nType == 2 -> TrimEnd ( del Part1) + local dXOffset = 0 + if not bOnLoop then bOnLoop = false end + if dAngBetween > 0 then + if nType == 1 then + -- trim start + local dDeltaStart = - dTh1 / sin(dAngBetween) + dLen2 = dLen2 + dDeltaStart + dXOffset = dDeltaStart + -- extend end + dLen1 = dLen1 + dTh1 * tan(90- math.abs(dAngBetween)) + elseif nType == 2 then + -- trim end + dLen1 = dLen1 - dTh2 / sin(dAngBetween) + -- extend start + local dDeltaStart = dTh2 * tan(90- math.abs(dAngBetween)) + dLen2 = dLen2 + dDeltaStart + dXOffset = dDeltaStart + end + else + -- qui sto estendendo le lunghezze, infatti gli angoli sono nergativi e quindi anche il loro seno + if nType == 1 then + -- il trim start diventa un extend end + local dDelta = - dTh2 / sin(dAngBetween) + if not bOnLoop then dDelta = dDelta - dTh1 * tan(90 - math.abs(dAngBetween)) end + dLen1 = dLen1 + dDelta + -- accorcio lo start + local dDeltaStart = - dTh2 * tan(90- math.abs(dAngBetween)) + dLen2 = dLen2 + dDeltaStart + dXOffset = dDeltaStart + elseif nType == 2 then + -- il trim end diventa un extend start + local dDeltaStart = - dTh1 / sin(dAngBetween) + if not bOnLoop then dDeltaStart = dDeltaStart - dTh2 * tan(90 - math.abs(dAngBetween)) end + dLen2 = dLen2 + dDeltaStart + dXOffset = math.abs(dDeltaStart) + -- accorcio l'end + dLen1 = dLen1 - dTh1 * tan(90- math.abs(dAngBetween)) + end + end + return dLen1, dLen2, dXOffset +end + +function AngleJunction(dAngBetween, dTh1, dTh2, dLen1, dLen2, bOnLoop) + -- modifico la lughezza dei lati solo se ho un angolo convesso + local dXOffest = 0 + if not bOnLoop then + local dDelta1 = dTh2 / sin( dAngBetween) + local dDelta2 = dTh1 / sin( dAngBetween) + if dAngBetween > 0 then + dLen1 = dLen1 - dDelta1 + dLen2 = dLen2 - dDelta2 + else + dLen1 = dLen1 + dDelta1 + dLen2 = dLen2 + dDelta2 + end + end + return dLen1, dLen2, dXOffest +end + +function ManageJunction(dAngBetween, dTh1, dTh2, nType, dLen1, dLen2, bOnLoop) + --nJunctionType -- 1 TrimStart, 2 TrimEnd, 3Ang + if nType == 1 or nType == 2 then + return TJunction(dAngBetween, dTh1, dTh2, nType, dLen1, dLen2, bOnLoop) + elseif nType == 3 then + return AngleJunction(dAngBetween, dTh1, dTh2, dLen1, dLen2, bOnLoop) + end +end + +function TOOL.CreateAdjustedPart( nLayOutloop, dLen, dH, dBeta1, dBeta2) + -- genero la regione piana del rettangolo deformato : + -- dLen è la lunghezza del lato su cui si va ad agganciare il pezzo che sto creando, quindi è un dato fisso + -- bisogna calcolare gli altri tre lati del quadrilatero + -- dProj1 dProj2 + -- __|_____________________________|__ + -- \ / | + -- \ beta1 beta2 / |dH + -- \ /___________dLen__________\ / | + -- beta 1 e beta 2 sono gli angoli alla base + -- dLen1 e dLen2 sono le proiezioni delle diagonali sulla base maggiore + -- beta 1 e beta 2 possono essere < 90 e quindi potrei avere anche un trapezio ribaltato, oppure un quasi parallelogramma + if dBeta1 == nil then dBeta1 = 90 end + if dBeta2 == nil then dBeta2 = 90 end + local dProj1 = dH * tan( dBeta1 - 90) + local dProj2 = dH * tan( dBeta2 - 90) + + local pt1 = ORIG() + local pt2 = Point3d(dLen,0,0) + local nLine1 = EgtLine( nLayOutloop, pt1, pt2) + EgtSetName(nLine1, "A1") + local pt3 = Point3d(dLen + dProj2,dH,0) + local nLine2 = EgtLine( nLayOutloop, pt2, pt3) + EgtSetName(nLine2, "A2") + local pt4 = Point3d( dProj1,dH,0) + local nLine3 = EgtLine( nLayOutloop, pt3, pt4) + EgtSetName(nLine3, "A3") + local nLine4 = EgtLine( nLayOutloop, pt4, pt1) + EgtSetName(nLine4, "A4") + TOOL.SetMachiningInfo(nLayOutloop, false) + return {nLine1, nLine2, nLine3, nLine4} +end + +function TOOL.SetSideAng(nLay, sEdgeName, dAng) + local nEdge = EgtGetFirstNameInGroup( nLay, sEdgeName) + EgtSetInfo( nEdge, 'SideAng', dAng) + EgtSetInfo( nEdge, 'OrigSideAng', dAng) +end + +-- ptCenter sono le coordinate del centro del foro rispetto all'angolo in basso a sinistra +function TOOL.CreateCircularHole(nPart, ptCenter, dDiam) + local nInLoopLay = EgtGroup(nPart) + EgtSetName(nInLoopLay, 'InLoop') + local HoleId = EgtCircle( nInLoopLay, ptCenter, dDiam, GDB_RT.GLOB) + TOOL.SetMachiningInfo(nInLoopLay, true) +end + + +function TOOL.CreateParetina(i, tbIdLoopTC, tbInfo) + local nPrev = i > 1 and i - 1 or #tbIdLoopTC + local nNext = i < #tbIdLoopTC and i + 1 or 1 + local dPairAngPrev = EgtGetInfo(tbInfo.nPrev, 'PairAng', 'd') or 0 + local dPairAngNext = EgtGetInfo(tbInfo.nNext, 'PairAng', 'd') or 0 + local dPairAng = EgtGetInfo(tbInfo.nId, 'PairAng', 'd') or 0 + local vtDirCurr = EgtSV( tbIdLoopTC[i], GDB_RT.GLOB) + local vtDirNext = EgtSV( tbIdLoopTC[nNext], GDB_RT.GLOB) + local vtDirPrev = EgtEV( tbIdLoopTC[nPrev], GDB_RT.GLOB) + local dLen = EgtCurveLength(tbIdLoopTC[i]) + local dLenPrev = EgtCurveLength(tbIdLoopTC[#tbIdLoopTC]) + local dLenNext = EgtCurveLength(tbIdLoopTC[nNext]) + local PAng, NAng = GetPrevNextAng(tbIdLoopTC[i]) + local dTh = EgtGetInfo(tbInfo.nId, 'dTh','d') + + -- calcolo l'angolo di sformo con il pezzo precedente + local dXOffset = 0 + -- se i due pezzi hanno angoli di accoppiamento discordi allora uno sta sotto e uno sta sopra + local bSameSide = dPairAng * dPairAngPrev > 0 + if bSameSide then + if tbInfo.nJunctionType == 3 then + local dSideAng_4, _, dBeta_DX = CalcDraftAngle( vtDirPrev, vtDirCurr, dPairAngPrev, dPairAng, PAng) + tbInfo.dAngBR = 180 - dBeta_DX + if tbInfo.bOnLoop then dSideAng_4 = dSideAng_4 * (-1) end + if PAng < 0 then dSideAng_4 = dSideAng_4 * (-1) end + tbInfo.dSideAngR = dSideAng_4 + if not tbInfo.bOnLoop then + dLenPrev, dLen, dXOffset = ManageJunction(PAng,dTh, dTh,tbInfo.nJunctionType, dLenPrev, dLen) + end + else + -- se ho una giunzione a T allora devo aggiustare la lunghezza dei pezzi sia che la faccia sia On, sia che sia Off + dLenPrev, dLen, dXOffset = ManageJunction(PAng,dTh, dTh,tbInfo.nJunctionType, dLenPrev, dLen) + -- setto il sideang da giunzione a T + -- setto il sideang da giunzione a T + local dSideAng_4 = 90 - math.abs(PAng) + if tbInfo.bOnLoop then dSideAng_4 = dSideAng_4 * (-1) end + tbInfo.dSideAngR = dSideAng_4 + end + else + -- setto il sideAng da giunzione a T (che va bene anche se la giunzione è angolata ma senza pezzo precedente) + local dSideAng = PAng < 0 and (90 + PAng) or 90-PAng + if tbInfo.bOnLoop then dSideAng = dSideAng * (-1) end + tbInfo.dSideAngR = dSideAng + -- visto che il pezzo precedente non è dallo stesso lato allora corrego l'estensione del pezzo corrente (in funzione del suo spessore) + if not tbInfo.bOnLoop then + local dOffset = dTh * tan( 90 - PAng) + dLen = dLen + dOffset + if tbInfo.nJunctionType == 1 then dXOffset = dXOffset + dOffset end + end + end + -- -- calcolo l'angolo di sformo con il pezzo successivo + bSameSide = dPairAng * dPairAngNext > 0 + if bSameSide then + if tbInfo.nJunctionType == 3 then + local dSideAng_2, dBeta_SX, __ = CalcDraftAngle( vtDirCurr, vtDirNext, dPairAng, dPairAngNext, NAng) + tbInfo.dAngBL = 180 - dBeta_SX + if tbInfo.bOnLoop then dSideAng_2 = dSideAng_2 * (-1) end + if NAng < 0 then dSideAng_2 = dSideAng_2 * (-1) end + tbInfo.dSideAngL = dSideAng_2 + if not tbInfo.bOnLoop then + dLen, dLenNext = ManageJunction(NAng, dTh, dTh, tbInfo.nJunctionType, dLen, dLenNext) + end + else + -- se ho una giunzione a T allora devo aggiustare la lunghezza dei pezzi sia che la faccia sia On, sia che sia Off + dLen, dLenNext = ManageJunction(NAng, dTh, dTh, tbInfo.nJunctionType, dLen, dLenNext) + -- setto il sideang da giunzione a T + local dSideAng_2 = 90 - math.abs(NAng) + if tbInfo.bOnLoop then dSideAng_2 = dSideAng_2 * (-1) end + tbInfo.dSideAngL = dSideAng_2 + end + else + -- setto il sideAng da giunzione a T (che va bene anche se la giunzione è angolata ma senza pezzo successivo) + local dSideAng = NAng < 0 and (90 + NAng) or 90-NAng + if tbInfo.bOnLoop then dSideAng = dSideAng * (-1) end + tbInfo.dSideAngL = dSideAng + -- visto che il pezzo successivo non è dallo stesso lato allora correggo l'estensione del pezzo corrente (in funzione del suo spessore) + if not tbInfo.bOnLoop then + local dOffset = dTh * tan( 90 - NAng) + dLen = dLen + dOffset + if tbInfo.nJunctionType == 2 then dXOffset = dXOffset + dOffset end + end + end + tbInfo.dLen = dLen + tbInfo.dXOffset = dXOffset +end + +return TOOL