Files
StoneSolidGen/TemplateTool.lua
T

747 lines
29 KiB
Lua

-- 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
TOOL.nId = GDB_ID.NULL
TOOL.nLay = GDB_ID.NULL
TOOL.nEdgeId = GDB_ID.NULL
TOOL.tbInfo = {}
TOOL.nPrev = -1
TOOL.nNext = -1
TOOL.nJunctionType = -1
TOOL.bOnLoop = nil
TOOL.dAngBR = nil
TOOL.dSideAngR = nil
TOOL.dAngBL = nil
TOOL.dSideAngL = nil
TOOL.dLen = nil
TOOL.dH = nil
TOOL.dXOffset = nil
TOOL.dBeta1 = nil
TOOL.dBeta2 = nil
function TOOL.SaveMePlease()
EgtSaveFile('D:\\Temp\\marmo\\Vein3D\\FOO.nge')
end
local function FindEdges(nLay)
local tbId = {}
local nId = EgtGetFirstInGroup(nLay)
while nId do
table.insert(tbId, nId)
nId = EgtGetNext(nId)
end
return tbId
end
local function FillInfoTable()
TOOL.tbInfo.nPrev = TOOL.nPrev
TOOL.tbInfo.nNext = TOOL.nNext
TOOL.tbInfo.nJunctionType = TOOL.nJunctionType
TOOL.tbInfo.bOnLoop = TOOL.bOnLoop
TOOL.tbInfo.dAngBR = TOOL.dAngBR
TOOL.tbInfo.dSideAngR = TOOL.dSideAngR
TOOL.tbInfo.dAngBL = TOOL.dAngBL
TOOL.tbInfo.dSideAngL = TOOL.dSideAngL
TOOL.tbInfo.dLen = TOOL.dLen
TOOL.tbInfo.dH = TOOL.dH
TOOL.tbInfo.dBeta1 = TOOL.dBeta1
TOOL.tbInfo.dBeta2 = TOOL.dBeta2
end
function TOOL.WriteDataToChildPart(nParent, nPart, nEdge, dLen, dAngDx, dAngSx, dH, dTh, dBeta1, dBeta2)
if not nPart then do return end end
if nParent then EgtSetInfo(nParent,"A"..tostring(nEdge), nPart) end
if nParent then EgtSetInfo(nPart, 'Parent', nParent) end
if nEdge then EgtSetInfo(nPart, 'ParentEdge', nEdge) end
if dLen then EgtSetInfo(nPart, 'Len', dLen) end
if dAngDx then EgtSetInfo(nPart, 'dAngDx', dAngDx) end
if dAgnSx then EgtSetInfo(nPart, 'dAngSx', dAngSx) end
if dH then EgtSetInfo(nPart, 'dH', dH) end
if dTh then EgtSetInfo(nPart, 'dTh', dTh) end
if dBeta1 then EgtSetInfo(nPart, 'dBeta1', dBeta1) end
if dBeta2 then EgtSetInfo(nPart, 'dBeta2', dBeta2) end
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)
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
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)
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
--local bInvertCurve = false
if bInLoop then
local IdOutRegion = EgtGetPrev(IdReg)
local vtNorm1 = EgtSurfFrNormVersor(IdOutRegion)
local vtNorm2 = EgtSurfFrNormVersor(IdReg)
if AreOppositeVectorApprox( vtNorm1, vtNorm2) then
EgtInvertSurf(IdReg)
--bInvertCurve = true
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
--if bInvertCurve then
-- for i = 1, #tbIdEntCrv do
-- EgtInvertCurve(tbIdEntCrv[i])
-- end
--end
return
end
-- definisco spessore pezzo
if dTh then EgtSetInfo(IdPart, 'Th', dTh) end
-- 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
-- --
function TOOL.AddLoopToLayer(nLay, tbIdLoop, dOffset, bInvert, bInLoop)
-- local tbLoop = {}
-- for i = 1, #tbIdLoop do
-- local nNewId = EgtCopyGlob(tbIdLoop[i], nLay)
-- if bInvert then EgtInvertCurve(nNewId) end
-- table.insert(tbLoop, nNewId)
-- end
-- TOOL.SetMachiningInfo(nLay, bInLoop)
--return tbLoop
local nNewLoop = EgtCurveCompoByChain(nLay, tbIdLoop, EgtSP(tbIdLoop[1], GDB_RT.GLOB), false)
if bInvert then EgtInvertCurve(nNewLoop) end
if dOffset > 0 then EgtOffsetCurve(nNewLoop, dOffset, GDB_OT.EXTEND) end
local tbNewLoop = TOOL.ExplodeAndNameEdges( nNewLoop, bInLoop)
return tbNewLoop
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 = 180 - dPairAng1
local dAngTilt2 = 180 - dPairAng2
local vtN1 = Vector3d({0,0,100})
local vtN2 = Vector3d({0,0,100})
vtN1:rotate(vtDir1, dAngTilt1)
vtN2:rotate(vtDir2, 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)
if (dPairAng2 > 90 and dBeta1 > 90) or (dPairAng2 < 90 and dBeta1 < 90) then dBeta1 = 180 - dBeta1 end
local dBeta2 = GetAngle( vtDir2, vtPerp)
if (dPairAng1 > 90 and dBeta2 > 90) or (dPairAng1 < 90 and dBeta2 < 90) then dBeta2 = 180 - dBeta2 end
local dSideAng = 0
dSideAng = (180 - dAng3d) / 2
--debug
EgtOutLog(tostring(dSideAng)..' '.. tostring(dBeta1).. ' '..tostring(dBeta2))
--debug
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
-- recupero eventuali input mancanti dalla tabella generale
if not dLen then dLen = TOOL.dLen end
if not dH then dH = TOOL.dH end
if not dBeta1 then dBeta1 = TOOL.dBeta1 end
if not dBeta2 then dBeta2 = TOOL.dBeta2 end
-- creo i lati del pezzo
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)
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)
TOOL.CreatePart(TOOL.FindLayers(nPart),nil,{HoleId},nil,true)
end
--function TOOL.CreateParetina(i, tbIdLoopTC, tbInfo, dPairAngCorr)
function TOOL.CreateParetina(nEdgeId, tbInfo, dPairAngCorr)
-- se non ho ricevuto input li recupero dalla tabella generale
if not nEdgeId then nEdgeId = TOOL.nEdgeId end
if not tbInfo then
FillInfoTable()
tbInfo = TOOL.tbInfo
end
local nLay = EgtGetParent(nEdgeId)
local tbIdLoopTC = FindEdges(nLay) -- tabella che contiene gli id degli Edge del loop
-- local nId = EgtGetFirstInGroup(nLay)
local i = tbInfo.nEdge -- posizione del lato nel layer del loop
if dPairAngCorr == nil then dPairAngCorr = 0 end
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) + dPairAngCorr
local dPairAngNext = (EgtGetInfo(tbInfo.nNext, 'PairAng', 'd') or 0) + dPairAngCorr
local dPairAng = (EgtGetInfo(tbInfo.nId, 'PairAng', 'd') or 0) + dPairAngCorr
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 PrevAng, NextAng = 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, PrevAng)
--tbInfo.dAngBR = 180 - dBeta_DX
tbInfo.dAngBR = dBeta_DX
if tbInfo.bOnLoop then dSideAng_4 = dSideAng_4 * (-1) end
if PrevAng < 0 then dSideAng_4 = dSideAng_4 * (-1) end
tbInfo.dSideAngR = dSideAng_4
if not tbInfo.bOnLoop then
dLenPrev, dLen, dXOffset = ManageJunction(PrevAng,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(PrevAng,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(PrevAng)
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 = PrevAng < 0 and (90 + PrevAng) or 90-PrevAng
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 - PrevAng)
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, NextAng)
-- tbInfo.dAngBL = 180 - dBeta_SX
tbInfo.dAngBL = dBeta_SX
if tbInfo.bOnLoop then dSideAng_2 = dSideAng_2 * (-1) end
if NextAng < 0 then dSideAng_2 = dSideAng_2 * (-1) end
tbInfo.dSideAngL = dSideAng_2
if not tbInfo.bOnLoop then
dLen, dLenNext = ManageJunction(NextAng, 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(NextAng, dTh, dTh, tbInfo.nJunctionType, dLen, dLenNext)
-- setto il sideang da giunzione a T
local dSideAng_2 = 90 - math.abs(NextAng)
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 = NextAng < 0 and (90 + NextAng) or 90-NextAng
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 - NextAng)
dLen = dLen + dOffset
if tbInfo.nJunctionType == 2 then dXOffset = dXOffset + dOffset end
end
end
tbInfo.dLen = dLen
tbInfo.dXOffset = dXOffset
end
function TOOL.CreateParetinaFull()
-- devo modificare anche la paretina precedente e la successiva
TOOL.CreateParetina()
end
return TOOL