Boîtes englobantes

Forum destiné aux questions et discussions en français
Forum rules
Be nice to others! Read the FreeCAD code of conduct!
User avatar
-alex-
Veteran
Posts: 1861
Joined: Wed Feb 13, 2019 9:42 pm
Location: France

Re: Boîtes englobantes

Post by -alex- »

FC_Menuiserie wrote: Mon May 17, 2021 11:16 am Cependant, je me suis rendu compte, après plus amples réflexions, que mon problème n'était pas uniquement lié aux boîtes englobantes parallèles aux axes.
J'ai bien compris, tu veux une boîte englobante qui soit orientée et qui corresponde aux brut capable de ton objet suivant un axe préférentiel.
Pour un simple rond avec Lattice2 il est possible d'attacher la boîte englobante par exemple sur l'intertie de l'objet:
Lattice2_boundingbox_simple_shape.gif
Lattice2_boundingbox_simple_shape.gif (430.01 KiB) Viewed 1926 times

Pour une forme plus complexe l'attachement doit être plus soigné, il demande une appréciation au cas par cas. Si la géométrie de l'objet évolue l'attachement peut ne plus correspondre au capable matière (mais peut être mis à jour):
Lattice2_boundingbox_fancy_shape.gif
Lattice2_boundingbox_fancy_shape.gif (487.67 KiB) Viewed 1926 times
User avatar
papyblaise
Veteran
Posts: 8025
Joined: Thu Jun 13, 2019 4:28 pm
Location: France

Re: Boîtes englobantes

Post by papyblaise »

une dernière solution simple comme Bonjour :
Bonjour > "Préférence > Sketcher > Affichage > restaurer position camera après édition :tu décoche
Merci Freedman sur le site anglais
Ainsi tu clik la face à mettre "de face" tu ouvre le sketcher > la dite face est parallèle à l'écran , tu ferme , elle le reste , t'as plus qu'à l'envoyer sur la page techdraw elle sera "de face"
il me semblait que c'était comme ça dans d'ancienne version , ou avais-je fais cette manip sans le savoir :?:
User avatar
FC_Menuiserie
Posts: 65
Joined: Thu Mar 18, 2021 10:28 am
Location: Arras (62), France

Re: Boîtes englobantes

Post by FC_Menuiserie »

Papyblaise, même si c'est simple comme bonjour, je ne comprends pas la méthode.
Décocher la cas dans les préférences c'est bon mais, mes Bodies ont, le plus souvent, plusieurs Pads, donc plusieurs Sketches. Du coup, lequel ouvrir une fois la face sélectionnée ?
Jean-Luc
On apprend de ses erreurs. J'ai encore bien appris aujourd'hui !
User avatar
papyblaise
Veteran
Posts: 8025
Joined: Thu Jun 13, 2019 4:28 pm
Location: France

Re: Boîtes englobantes

Post by papyblaise »

Le pb est que tous les Pad d'un même body ne forme qu'une seule pièce
il aurait fallu que chaque pièce soit dans un body séparé
C'est la seule solution dans un exercice comme ton cas pour détailler chaque barreau un par un
User avatar
FC_Menuiserie
Posts: 65
Joined: Thu Mar 18, 2021 10:28 am
Location: Arras (62), France

Re: Boîtes englobantes

Post by FC_Menuiserie »

C'est pour ça que la solution Body dans un Part me convient bien.
Je défini le Body dans son repère et c'est son Part que j'oriente et déplace. Ainsi, à tout moment, la BoundingBox du Body est conforme à ce que j'attends et les dimension XLength, YLength et ZLength sont correctes.
Pour mon projet en cours je fais comme cela.
Par la suite je regarderai la solution proposée par -alex- en ayant une petite expérience.
Jean-Luc
On apprend de ses erreurs. J'ai encore bien appris aujourd'hui !
User avatar
FaDa3D
Posts: 874
Joined: Tue Aug 08, 2017 8:21 am
Location: Savoie France

Re: Boîtes englobantes

Post by FaDa3D »

Bonjour à tous,
A mon avis les directions du parallélépipède minimal capable d'une pièce sont les mêmes que celles des moments d'inertie principaux de cette pièce. Mais comment trouver ces directions ? Faudra ensuite trouver les dimensions de cette boite. Avis aux programmateurs courageux.
Salutations.
Fada de 3D.
Linux Mint
User avatar
flachyjoe
Veteran
Posts: 1891
Joined: Sat Mar 31, 2012 12:00 pm
Location: Limoges, France

Re: Boîtes englobantes

Post by flachyjoe »

Salut,
FaDa3D wrote: Thu May 20, 2021 12:04 pm A mon avis les directions du parallélépipède minimal capable d'une pièce sont les mêmes que celles des moments d'inertie principaux de cette pièce.
sans doute pour un parallélépipède plein, mais dès que tu as une forme tarabiscotée voir même simplement un cube troué, ce n'est plus valable.
Capture d’écran_2021-05-20_14-11-00.png
Capture d’écran_2021-05-20_14-11-00.png (37.47 KiB) Viewed 1764 times
- Flachy Joe -
Image
User avatar
FaDa3D
Posts: 874
Joined: Tue Aug 08, 2017 8:21 am
Location: Savoie France

Re: Boîtes englobantes

Post by FaDa3D »

flachyjoe wrote: Thu May 20, 2021 12:11 pm sans doute pour un parallélépipède plein, mais dès que tu as une forme tarabiscotée voir même simplement un cube troué, ce n'est plus valable.
Démonstration ?
Fada de 3D.
Linux Mint
User avatar
flachyjoe
Veteran
Posts: 1891
Joined: Sat Mar 31, 2012 12:00 pm
Location: Limoges, France

Re: Boîtes englobantes

Post by flachyjoe »

FaDa3D wrote: Thu May 20, 2021 12:15 pm Démonstration ?
cf l'image de mon post : l'axe d'inertie n'est clairement pas orienté sur un axe du cube.
- Flachy Joe -
Image
User avatar
flachyjoe
Veteran
Posts: 1891
Joined: Sat Mar 31, 2012 12:00 pm
Location: Limoges, France

Re: Boîtes englobantes

Post by flachyjoe »

Voila une macro qui tourne un objet pour minimiser le volume de la boite englobante, cf la vue rapport pour la taille finale.
Capture d’écran_2021-05-20_23-11-44.png
Capture d’écran_2021-05-20_23-11-44.png (43.47 KiB) Viewed 1676 times
Sélectionnez l'objet et lancer la macro, une copie simple est créée.

Code: Select all

# -*- coding: utf-8 -*-

#Stop conditions
EPSILON = 1e-4 #mm² : minimum gain for face area optimization
MAXITER = 1e2 #maximum count for each loop

def BBVol(bb):
	'''returns the given BoundBox volume'''
	return bb.XLength*bb.YLength*bb.ZLength

def BBSize(bb):
	'''returns a string representation of a BoundBox'''
	return "size (x,y,z) : %g %g %g volume : %g mm³" % (bb.XLength, bb.YLength, bb.ZLength, BBVol(bb) )

if len(Gui.Selection.getSelection()) != 1:
	raise ValueError("Please select ONE object")

s=Gui.Selection.getSelection()[0].Shape.copy() #simple copy of the selected object
Msg("initial %s %s\n" %  (s.BoundBox, BBSize(s.BoundBox)))

UPSILON = s.Volume/1e6 # minimum gain for volume optimization
Msg("volume gain stop condition : %g mm³\n" % UPSILON)

# main loop initialization
angleX = angleY = angleZ = 0
gItter = 0
gDeltaAngle = 45 

initVol = minVol = lastVol = gDelta = BBVol(s.BoundBox)

# main loop which minimize boundbox volume
while abs(gDelta) > UPSILON and gItter < MAXITER:
	
	#sub-loops minimize boundbox face area in the rotation axis direction
	
	#Z axis, XY face
	deltaAngle = gDeltaAngle
	minArea = lastArea  =  deltaXY = s.BoundBox.XLength *  s.BoundBox.YLength
	itter = 0
	while abs(deltaXY) > EPSILON and itter < MAXITER:
		angleZ += deltaAngle
		s.Placement.Rotation = App.Rotation(angleZ, angleY, angleX)
		newArea = s.BoundBox.XLength * s.BoundBox.ZLength
		deltaXY = lastArea - newArea
		if newArea >= minArea:	 #if this step increases the face area
			deltaAngle = - deltaAngle/2 #switch rotation direction and reduce movement
		else:
			minArea  = newArea	#keep rotation direction and amount until volume increase
		lastArea  = newArea
		itter += 1

	#Y axis, XZ face
	deltaAngle = gDeltaAngle
	minArea = lastArea  =  s.BoundBox.XLength *  s.BoundBox.ZLength
	deltaXZ = lastArea
	itter = 0
	while abs(deltaXZ) > EPSILON and itter < MAXITER:
		angleY += deltaAngle
		s.Placement.Rotation = App.Rotation(angleZ, angleY, angleX)
		newArea = s.BoundBox.XLength * s.BoundBox.ZLength
		deltaXZ = lastArea - newArea
		if newArea >= minArea:
			deltaAngle = - deltaAngle/2
		else:
			minArea  = newArea
		lastArea  = newArea
		itter += 1

	#X axis, YZ face
	deltaAngle = gDeltaAngle
	minArea = lastArea  = s.BoundBox.YLength *  s.BoundBox.ZLength
	deltaYZ =lastArea
	itter = 0
	while abs(deltaYZ) > EPSILON and itter < MAXITER:
		angleX += deltaAngle
		s.Placement.Rotation = App.Rotation(angleZ, angleY, angleX)
		newArea = s.BoundBox.YLength *  s.BoundBox.ZLength
		deltaYZ = lastArea - newArea
		if newArea >= minArea:
			deltaAngle = - deltaAngle/2
		else:
			minArea  = newArea
		lastArea  = newArea
		itter += 1

	#compute stop criterion
	newVol =  BBVol(s.BoundBox)
	gDelta = lastVol - newVol

	if newVol >= minVol:	#if this step increases the boundbox volume
		gDeltaAngle = -gDeltaAngle/2 #switch rotation direction and reduce movement
	else:
		minVol  = newVol	#keep rotation direction and amount until volume increase
	lastVol = newVol
	gItter += 1

Msg("nb itter : %i, last delta  : %g mm³, angleX :  %g, angleY :  %g\n" % (gItter ,gDelta, angleX, angleY))
Msg("%s %s\n" % (s.BoundBox, BBSize(s.BoundBox)))
Msg("gain : %g %%\n" % ((initVol - BBVol(s.BoundBox))/initVol * 100))
Part.show(s, "BBOptimized")
EDIT 21/05/21: code commenté
Last edited by flachyjoe on Fri May 21, 2021 12:18 pm, edited 1 time in total.
- Flachy Joe -
Image
Post Reply