diff --git a/LuaLibs/BasicCustomerStrategies.lua b/LuaLibs/BasicCustomerStrategies.lua index 31b3d09..85e2473 100644 --- a/LuaLibs/BasicCustomerStrategies.lua +++ b/LuaLibs/BasicCustomerStrategies.lua @@ -57,7 +57,7 @@ local function GetStrategies_Egalware( Proc) --------------------------------------------------------------------- -- Feature : Longitudinal Cut (0-10) elseif ID.IsLongitudinalCut( Proc) then - Strategies = { { sStrategyId = 'STR0002'}, { sStrategyId = 'STR0005'}} + Strategies = { { sStrategyId = 'STR0002'}, { sStrategyId = 'STR0005'}, { sStrategyId = 'STR0010'}} --------------------------------------------------------------------- -- Feature : Double Cut (1-11) elseif ID.IsDoubleCut( Proc) then @@ -65,6 +65,7 @@ local function GetStrategies_Egalware( Proc) --------------------------------------------------------------------- -- Feature : Ridge or Valley Cut (0-12) elseif ID.IsDoubleLongitudinalCut( Proc) then + Strategies = { { sStrategyId = 'STR0010'}} --------------------------------------------------------------------- -- Feature : Saw Cut (0-13) elseif ID.IsSawCut( Proc) then @@ -376,7 +377,7 @@ local function GetStrategies_Essetre( Proc) --------------------------------------------------------------------- -- Feature : Longitudinal Cut (0-10) elseif ID.IsLongitudinalCut( Proc) then - Strategies = { { sStrategyId = 'STR0002'}, { sStrategyId = 'STR0005'}} + Strategies = { { sStrategyId = 'STR0002'}, { sStrategyId = 'STR0005'}, { sStrategyId = 'STR0010'}} --------------------------------------------------------------------- -- Feature : Double Cut (1-11) elseif ID.IsDoubleCut( Proc) then @@ -384,6 +385,7 @@ local function GetStrategies_Essetre( Proc) --------------------------------------------------------------------- -- Feature : Ridge or Valley Cut (0-12) elseif ID.IsDoubleLongitudinalCut( Proc) then + Strategies = { { sStrategyId = 'STR0010'}} --------------------------------------------------------------------- -- Feature : Saw Cut (0-13) elseif ID.IsSawCut( Proc) then diff --git a/Process.lua b/Process.lua index cd14639..af3ba4a 100644 --- a/Process.lua +++ b/Process.lua @@ -53,7 +53,7 @@ _G.package.loaded['TAILCUT\\TAILCUT'] = nil -- Infatti difficile ci siano 9999 strategie. -- reset strategie caricate come librerie for i = 1, 9999 do - local IdSTRTemp = EgtReplaceString( tostring( i/10000, 4), '0.', '') + local IdSTRTemp = EgtReplaceString( EgtNumToString( i/10000, -4), '0.', '') local sLibraryToReload = "STR" .. IdSTRTemp .. "\\STR" .. IdSTRTemp if _G.package.loaded[sLibraryToReload] then _G.package.loaded[sLibraryToReload] = nil diff --git a/Strategies/AvailableStrategyList.json b/Strategies/AvailableStrategyList.json index f5b4d47..88d665c 100644 --- a/Strategies/AvailableStrategyList.json +++ b/Strategies/AvailableStrategyList.json @@ -16,7 +16,7 @@ "nGrp": "0", "TopologyList" : [ { "sName": "Feature", - "StrategyList" : [ { "sStrategyID": "STR0002" }, { "sStrategyID": "STR0005" } ] + "StrategyList" : [ { "sStrategyID": "STR0002" }, { "sStrategyID": "STR0005" }, { "sStrategyID": "STR0010" }] } ] }, @@ -36,7 +36,7 @@ "nGrp": "0", "TopologyList" : [ { "sName": "Feature", - "StrategyList" : [ ] + "StrategyList" : [ { "sStrategyID": "STR0010" }] } ] }, diff --git a/Strategies/Standard/HEADCUT/HEADCUT.lua b/Strategies/Standard/HEADCUT/HEADCUT.lua index cd208ac..a7ad22b 100644 --- a/Strategies/Standard/HEADCUT/HEADCUT.lua +++ b/Strategies/Standard/HEADCUT/HEADCUT.lua @@ -5,7 +5,9 @@ --------------------------------------------------------------------------------------------------------- --- TODO: HEADCUT copiata da SPLITCUT. Da sistemare e capire se fare solo una strategia oppure due divise. +-- TODO: SPLITCUT è una funzione di base e si occupa di fare lo split, cioè considernado come se la trave fosse molto lunga e motore non interferisce mai +-- HEADCUT è figlia della TAILCUT. Le due strategie sono identiche in caso di rimozione del grezzo in eccesso. La TAILCUT ha in più la gestione dello split +-- Decidere se lasciare HEADCUT e TAILCUT divise, oppure se uniformarle e chiamare una o l'altra in base alla feature alla quale sono applicate. --------------------------------------------------------------------------------------------------------- @@ -204,7 +206,7 @@ local function GetSplitStrategy( Proc, Part) -- ChainSawHorizontal (motosega) -- ChainSawSideSingle (motosega) -- ChainSawSideDouble (motosega) - -- ChainSawPlusBlade (motosega pi� lama orizzontale) + -- ChainSawPlusBlade (motosega più lama orizzontale) -- Mill (svuotatura) end diff --git a/Strategies/Standard/STR0009/STR0009.lua b/Strategies/Standard/STR0009/STR0009.lua index bb09a69..0165610 100644 --- a/Strategies/Standard/STR0009/STR0009.lua +++ b/Strategies/Standard/STR0009/STR0009.lua @@ -55,7 +55,7 @@ local function GetArcStrategy( Proc, Part) if not bExecStrip then dDimStrip = 0 end - + -- se lavorazione orizzontale if bIsHorizontal then local bDouble @@ -127,7 +127,7 @@ local function GetArcStrategy( Proc, Part) else -- non si fa nulla end - -- altrimenti senmza codolo + -- altrimenti senza codolo else -- se utensile 1 esegue completamente if Milling.ToolInfo.nToolIndex and Milling.ToolInfo.dResidualDepth < 10 * GEO.EPS_SMALL then diff --git a/Strategies/Standard/STR0010/STR0010.json b/Strategies/Standard/STR0010/STR0010.json new file mode 100644 index 0000000..e22a162 --- /dev/null +++ b/Strategies/Standard/STR0010/STR0010.json @@ -0,0 +1,52 @@ +{ + "sStrategyId": "STR0010", + "ParameterList" : [ + { + "sName": "dAntiSplintWithBlade", + "sNameNge": "ANTISPLINT_BLADE", + "sValue": "false", + "sDescriptionShort": "Antisplint with blade", + "sDescriptionLong": "Use the blade as antisplint in case the geometry is not through", + "sType": "b", + "sMessageId": " ", + "sMinUserLevel": "1" + }, + { + "sName": "dExtendAfterTail", + "sNameNge": "EXTEND_AFTER_TAIL", + "sValue": "", + "sDescriptionShort": "", + "sDescriptionLong": "", + "sType": "d", + "sMessageId": " ", + "sMinUserLevel": "1" + }, + { + "sName": "sCanDamageNextPiece", + "sNameNge": "DAMAGE_NEXT_PIECE", + "sValue": "NEVER", + "sType": "combo", + "sMinUserLevel": "1", + "Choices": [ + { + "sValue": "NEVER", + "sDescriptionShort": "", + "sDescriptionLong": "", + "sMessageId": "" + }, + { + "sValue": "ONLY_IF_RAWPART", + "sDescriptionShort": "", + "sDescriptionLong": "", + "sMessageId": "" + }, + { + "sValue": "ALWAYS", + "sDescriptionShort": "", + "sDescriptionLong": "", + "sMessageId": "" + } + ] + } + ] +} \ No newline at end of file diff --git a/Strategies/Standard/STR0010/STR0010.lua b/Strategies/Standard/STR0010/STR0010.lua new file mode 100644 index 0000000..7438929 --- /dev/null +++ b/Strategies/Standard/STR0010/STR0010.lua @@ -0,0 +1,202 @@ +-- Strategia: STR0010 +-- Descrizione +-- fresatura perpendicolare +-- Feature: cut, longcut, ... + +-- carico librerie +local BeamLib = require( 'BeamLib') +local BeamData = require( 'BeamData') +local MachiningLib = require( 'MachiningLib') +local FeatureLib = require( 'FeatureLib') +-- strategie di base +local FaceByMill = require('FACEBYMILL') + +-- Tabella per definizione modulo +local STR0010 = {} +local Strategy = {} + +------------------------------------------------------------------------------------------------------------- +local function GetStrategyCompletionPercentage( Machinings) + local dCompletionPercentage = 0 + + local dCompletionPercentageNumerator = 0 + local dCompletionPercentageDenominator = 0 + local nWeightsCount = 0 + for i = 1, #Machinings do + local Machining = Machinings[i] + local dWeight = Machining.dResultWeight + if not dWeight or ( dWeight < 10 * GEO.EPS_SMALL) then + dWeight = 1 + else + nWeightsCount = nWeightsCount + 1 + end + -- il peso deve essere settato in tutte le lavorazioni o in nessuna + if ( nWeightsCount ~= 0) and ( nWeightsCount ~= i) then + error( 'GetWeightedCompletionPercentage : inconsistent weights') + end + local dWeightedCompletionPercentage = Machining.dCompletionPercentage / 100 * dWeight + if Machining.bIsApplicable then + dCompletionPercentageNumerator = dCompletionPercentageNumerator + dWeightedCompletionPercentage + end + dCompletionPercentageDenominator = dCompletionPercentageDenominator + dWeight + end + + dCompletionPercentage = min( 100 * dCompletionPercentageNumerator / dCompletionPercentageDenominator, 100) + + return dCompletionPercentage +end + +------------------------------------------------------------------------------------------------------------- +local function CompareEdges( EdgeA, EdgeB) + -- prima i lati orientati lungo X + if abs( EdgeA.vtN:getX()) < abs( EdgeB.vtN:getX()) - 10 * GEO.EPS_SMALL then + return true + elseif abs( EdgeA.vtN:getX()) > abs( EdgeB.vtN:getX()) + 10 * GEO.EPS_SMALL then + return false + -- se stessa X si preferiscono i lati più lunghi (nel caso di 5 lati è quello non spezzato) + else + if EdgeA.dLength > EdgeB.dLength + 10 * GEO.EPS_SMALL then + return true + elseif EdgeA.dLength < EdgeB.dLength - 10 * GEO.EPS_SMALL then + return false + -- se stessa lunghezza si preferiscono i lati più in basso + -- TODO qui dipenderà dalla lama scelta + else + if EdgeA.vtN:getZ() > EdgeB.vtN:getZ() + 10 * GEO.EPS_SMALL then + return true + elseif EdgeA.vtN:getZ() < EdgeB.vtN:getZ() - 10 * GEO.EPS_SMALL then + return false + -- se stessa Z si preferiscono i lati verso il fronte della trave + else + if EdgeA.vtN:getY() > EdgeB.vtN:getY() + 10 * GEO.EPS_SMALL then + return true + elseif EdgeA.vtN:getY() < EdgeB.vtN:getY() - 10 * GEO.EPS_SMALL then + return false + else + return false + end + end + end + end +end + +------------------------------------------------------------------------------------------------------------- +local function IsTopologyOk( Proc) + if Proc.Topology.sFamily == 'Bevel' then + return true + else + return false + end +end + +------------------------------------------------------------------------------------------------------------- +-- TODO modificare funzione e verificare pinzaggio con regioni e area outline +local function IsPositionOK( Proc, Part) + local bIsFeatureLong = FeatureLib.IsMachiningLong( Proc.b3Box:getDimX(), Part, { dMaxSegmentLength = BeamData.LONGCUT_ENDLEN}) + -- se impatta su faccia retro o sotto, controllo fattibilità + if Proc.AffectedFaces.bBack then + if ( bIsFeatureLong and Proc.b3Box:getDimZ() > Part.dHeight / 2) or ( not bIsFeatureLong and Proc.b3Box:getDimZ() > Part.dHeight / 2) then + return false + end + end + if Proc.AffectedFaces.bBottom then + if ( bIsFeatureLong and Proc.b3Box:getDimY() > Part.dHeight / 2) or ( not bIsFeatureLong and Proc.b3Box:getDimY() > Part.dHeight / 2) then + return false + end + end + + -- altrimenti fattibile + return true +end + +------------------------------------------------------------------------------------------------------------- +function STR0010.Make( bAddMachining, Proc, Part, CustomParameters) + -- carico parametri da default e li aggiorno con quelli passati dal chiamante (potrebbero non essere congruenti) + local StrategyLib = {} + StrategyLib.Config = STRATEGIES_CONFIG[CustomParameters.sStrategyId] + Strategy.sName = StrategyLib.Config.sStrategyId + Strategy.Parameters = BeamLib.LoadCustomParametersInStrategy( Proc, CustomParameters, StrategyLib.Config) + Strategy.Machinings = {} + Strategy.Result = {} + + -- controllo su topologia + if not IsTopologyOk( Proc) then + Strategy.Result = FeatureLib.GetStrategyResultNotApplicable( 'Strategy ' .. StrategyLib.Config.sStrategyId .. ' not implemented') + return false, Strategy.Result + end + + -- controllo dimensioni + if not IsPositionOK( Proc, Part) then + Strategy.Result = FeatureLib.GetStrategyResultNotApplicable( 'Feature not machinable in this position') + return false, Strategy.Result + end + + -- volume della feature + local dFeatureVolume = FeatureLib.GetFeatureVolume( Proc, Part) + + -- TODO taglio su eventuali facce di chiusura + + -- eventuali punti di spezzatura + local FeatureSplittingPoints = FeatureLib.GetFeatureSplittingPoints( Proc, Part) + local bIsSplitFeature = false + if #FeatureSplittingPoints > 0 then + bIsSplitFeature = true + end + + local dExtendAfterTail = Strategy.Parameters.dExtendAfterTail or max( Part.dDistanceToNextPiece - BeamData.CUT_EXTRA, 0) + if MachiningLib.CanExtendAfterTail( Strategy.Parameters.sCanDamageNextPiece, Part) then + dExtendAfterTail = 10000 + end + + -- si trova il lato della faccia di fondo da lavorare + local BottomEdgesSorted = {} + for i = 1, #Proc.MainFaces.BottomFaces[1].Edges do + table.insert( BottomEdgesSorted, Proc.MainFaces.BottomFaces[1].Edges[i]) + end + table.sort( BottomEdgesSorted, CompareEdges) + + -- lavorazione faccia bottom con fresa + local dDepthToMachine = BottomEdgesSorted[1].dElevation + 5 + local OptionalParametersFaceByMill = { dDepthToMachine = dDepthToMachine, bIsSplitFeature = bIsSplitFeature, dExtendAfterTail = dExtendAfterTail} + -- primo lato + local Milling = {} + Milling = FaceByMill.Make( Proc, Part, Proc.MainFaces.BottomFaces[1], BottomEdgesSorted[1], OptionalParametersFaceByMill) + + -- lavorazioni da applicare spostate in lista finale + table.insert( Strategy.Machinings, Milling) + + -- calcolo completamento, serve la lista di lavorazioni che comprende le non applicabili + Strategy.Result.dCompletionPercentage = GetStrategyCompletionPercentage( Strategy.Machinings) + Strategy.Result.nCompletionIndex = FeatureLib.GetFeatureCompletionIndex( Strategy.Result.dCompletionPercentage) + + local MachiningResult = MachiningLib.GetSplitMachinings( Strategy.Machinings, FeatureSplittingPoints, Part) + + -- calcolo risultati + if Strategy.Machinings[1].bIsApplicable then + Strategy.Result.nQuality = FeatureLib.GetStrategyQuality( MachiningResult) + Strategy.Result.dTimeToMachine = FeatureLib.GetStrategyTimeToMachine( MachiningResult) + Strategy.Result.dMRR = ( dFeatureVolume / Strategy.Result.dTimeToMachine) / pow( 10, 6) + if Strategy.Result.dCompletionPercentage > 100 - 10 * GEO.EPS_SMALL then + Strategy.Result.sStatus = 'Completed' + else + Strategy.Result.sStatus = 'Not-Completed' + end + else + Strategy.Result = FeatureLib.GetStrategyResultNotApplicable() + end + + local bAreAllMachiningsAdded = true + -- aggiunta lavorazioni + if bAddMachining and Strategy.Result.sStatus ~= 'Not-Applicable' then + -- aggiunge lavorazione + for j = 1, #MachiningResult do + bAreAllMachiningsAdded = MachiningLib.AddMachinings( Proc, MachiningResult[j]) + end + end + + return bAreAllMachiningsAdded, Strategy.Result +end + +------------------------------------------------------------------------------------------------------------- + + return STR0010 \ No newline at end of file diff --git a/StrategyLibs/FACEBYMILL.lua b/StrategyLibs/FACEBYMILL.lua index 5286d60..c748a43 100644 --- a/StrategyLibs/FACEBYMILL.lua +++ b/StrategyLibs/FACEBYMILL.lua @@ -81,7 +81,7 @@ local function CalculateLeadInOut( Machining, EdgeToMachine, Part) if Machining.bIsStartClosed or Machining.bIsEndClosed or Machining.CloneStepsRadial.nCount > 1 then - + Machining.sLeadInOutType = 'Perpendicular' if AreSameVectorApprox( Machining.vtToolDirection, EdgeToMachine.vtN) then LeadIn.dPerpDistance = EdgeToMachine.dElevation + BeamData.CUT_SIC - Machining.dRadialOffset