Comment créer rapidement un plan milieu ?

Forum destiné aux questions et discussions en français
Forum rules
Be nice to others! Read the FreeCAD code of conduct!
User avatar
Vincent B
Veteran
Posts: 4713
Joined: Sun Apr 05, 2015 9:02 am
Location: La Rochelle, France

Re: Comment créer rapidement un plan milieu ?

Post by Vincent B »

Sinon tout simplement le plan inertiel à cette face, puis tournée de 90°.
...
PS: pourquoi je ne peut pas changer la couleur de la pièce avec la version realthunder? grrr
Attachments
Capture.JPG
Capture.JPG (56 KiB) Viewed 1366 times
Grub
Posts: 303
Joined: Sun Nov 15, 2020 7:28 pm

Re: Comment créer rapidement un plan milieu ?

Post by Grub »

Il doit y avoir un problème de recompute avec la version branch 0.20 car je viens d'installer la weekly pour essayer : j'ouvre mon fichier version Realthunder, il suffit d'ouvrir et de fermer le Sketch du 1er Pad et la pièce est correcte. On peut aussi modifier la couleur sans problème.

Capture d’écran (94).png
Capture d’écran (94).png (216.69 KiB) Viewed 1345 times
Ta technique fonctionne quand le plan est bien "symétrique par rapport aux faces", là ce n'est pas le cas, c'était justement le piège :lol:


Bon, je n'avance pas sur une éventuelle macro, je n'arrive pas à comprendre comment récupérer le placement de la sélection de 2 faces et calculer le plan milieu (les vecteurs sont trop loins de moi :cry: ).
User avatar
flachyjoe
Veteran
Posts: 1869
Joined: Sat Mar 31, 2012 12:00 pm
Location: Limoges, France

Re: Comment créer rapidement un plan milieu ?

Post by flachyjoe »

Salut,
voila un premier jet de macro, il faut encore gérer le cas où les plans sont parallèles et rendre ça paramétrique. :ugeek:

Code: Select all

# MidPlane FreeCAD Macro
# FlachyJoe 2022

def main():
	doc = App.ActiveDocument
	
	# get selcted subobjects
	selEx=Gui.Selection.getSelectionEx()
	subs = [ sub for sel in selEx for sub in sel.SubObjects]
	
	# check selection validity
	if (len(subs) != 2 or any([(s.ShapeType != "Face") for s in subs])):
		Err('Please select two faces\n')
		return False
	
	# check planes creation
	planes = [s.findPlane() for s in subs]
	if not all(planes):
		Err('Please select two planar faces\n')
		return False
	
	resultPlane = doc.addObject('PartDesign::Plane', 'DatumPlane')

	# planes intersection
	intersectLine = planes[0].intersect(planes[1])
	if intersectLine:
		resultPlane.Placement.Base = intersectLine[0].Location
		rAxis = (planes[0].Axis - planes[1].Axis)/2
		resultPlane.Placement.Rotation = App.Rotation(rAxis, App.Vector(0,0,1))
	else:
		# Parallel case
		resultPlane.Placement.Base = (planes[0].Position +  planes[1].Position)/ 2
		resultPlane.Placement.Rotation = App.Rotation(planes[0].Axis, App.Vector(0,0,1))

main()
- Flachy Joe -
Image
Grub
Posts: 303
Joined: Sun Nov 15, 2020 7:28 pm

Re: Comment créer rapidement un plan milieu ?

Post by Grub »

flachyjoe wrote: Sun Jan 23, 2022 10:56 am Salut,
voila un premier jet de macro, il faut encore gérer le cas où les plans sont parallèles et rendre ça paramétrique. :ugeek:
Bravo et merci, c'est déjà un très bon début, je n'aurais pas été capable de coder cela. Mes compétences se limitent à enregistrer une macro et essayer de la modifier pour aboutir à mes fins...
Grub
Posts: 303
Joined: Sun Nov 15, 2020 7:28 pm

Re: Comment créer rapidement un plan milieu ?

Post by Grub »

Dans la macro j'ai besoin d'utiliser le nom d'un vertex d'une face sélectionnée (Vertex10 par exemple) mais je n'arrive qu'a récupérer les id des vertex comme cela :

Code: Select all

>>> face.Vertexes
[<Vertex object at 000002210661F550>, <Vertex object at 000002210661FB80>, <Vertex object at 0000022106620260>, <Vertex object at 0000022106620470>]
Quelqu'un pourrait me dire comment je peux avoir les noms en langage humain ? :D
User avatar
flachyjoe
Veteran
Posts: 1869
Joined: Sat Mar 31, 2012 12:00 pm
Location: Limoges, France

Re: Comment créer rapidement un plan milieu ?

Post by flachyjoe »

Grub wrote: Sun Jan 23, 2022 8:55 pm Quelqu'un pourrait me dire comment je peux avoir les noms en langage humain ? :D
En une ligne ça donne ça :

Code: Select all

>>> ['Vertex%i' % (i+1) for w in Shape.Faces[1].Vertexes for i,v in enumerate(Shape.Vertexes) if v.isEqual(w)]
['Vertex5', 'Vertex6', 'Vertex7', 'Vertex8']
NB : les indices python commences à 0 alors que ceux qui nomment les faces/arêtes/sommets commencent à 1, il faut donc ajouter 1 à l'indice python.
- Flachy Joe -
Image
Grub
Posts: 303
Joined: Sun Nov 15, 2020 7:28 pm

Re: Comment créer rapidement un plan milieu ?

Post by Grub »

flachyjoe wrote: Sun Jan 23, 2022 9:19 pm
Grub wrote: Sun Jan 23, 2022 8:55 pm Quelqu'un pourrait me dire comment je peux avoir les noms en langage humain ? :D
En une ligne ça donne ça :

Code: Select all

>>> ['Vertex%i' % (i+1) for w in Shape.Faces[1].Vertexes for i,v in enumerate(Shape.Vertexes) if v.isEqual(w)]
['Vertex5', 'Vertex6', 'Vertex7', 'Vertex8']
NB : les indices python commences à 0 alors que ceux qui nomment les faces/arêtes/sommets commencent à 1, il faut donc ajouter 1 à l'indice python.
Merci, je vais regarder ça.
Grub
Posts: 303
Joined: Sun Nov 15, 2020 7:28 pm

Re: Comment créer rapidement un plan milieu ?

Post by Grub »

J'ai avancé sur la macro, ça fonctionne en paramétrique, faut sélectionner 2 faces parallèles et executer la macro.

ça construit les géométries paramétriques nécessaires :
-Point sur centre de masse d'un plan
-Ligne normale au plan passant par le point
-Point sur ligne et plan opposé
-enfin plan milieu des 2 points

On cache les géométries superflues dans un groupe 'Geometries' et on ne garde que le plan milieu visible.

On économise pas mal de clics.

Bon, c'est codé à ma manière, pour moi c'est humainement lisible, c'est le principal ... On peut probablement faire beaucoup mieux mais c'est au-delà de mes compétences (s'il faut être codeur pour faire de la CAO, ça va vite limiter les emplois pourvus en entreprise :lol: )

A AJOUTER : Vérifier que les 2 faces sélectionées sont bien parallèles avant d'exécuter la macro.

Faut que je trouve une petite icone qui va bien et ça devrait faire parti de ma barre d'outils.

J'ai testé en 0.19, 0.20 et 0.20RT.
N'hésitez pas à tester et l'améliorer.

Code: Select all

#########################################################
#Macro pour créer un plan milieu parallèle à 2 faces
#
#Selectionner 2 faces parallèles d'un body et executer la macro
#
#A FAIRE : verifier que les 2 faces selectionnées sont bien parallèles
#
############################################################
from PySide import QtGui

def message():
	QtGui.QMessageBox.information(None,"","Sélectionner 2 faces parallèles")

def planmilieu():
	obj = s.ObjectName  # nom de l'object
	docname = s.DocumentName #nom du document
	Gui.Selection.clearSelection()
	
	###on crée un premier datum point sur centre masse du plan 1
	fpoint = App.getDocument(docname).getObject(body.Name).newObject('PartDesign::Point','P1') 
	Point1 = str(fpoint.Name) #on récupère le nom du point car different de P1 si le nom existe déjà
	App.getDocument(docname).getObject(Point1).Support = [(App.getDocument(docname).getObject(obj), nomFace1), ]
	App.getDocument(docname).getObject(Point1).MapMode = 'CenterOfMass'
	Gui.Selection.addSelection(str(docname),Point1) # on selectionne le point pour pouvoir le masquer
	Gui.runCommand('Std_ToggleVisibility',0) #on cache le point
	Gui.Selection.clearSelection()
		
	#### datum ligne normale au plan passant par le point
	fligne1 = App.getDocument(docname).getObject(body.Name).newObject('PartDesign::Line','L1')
	Ligne1 = str(fligne1.Name) 
	App.getDocument(docname).getObject(Ligne1).Support = [(App.getDocument(docname).getObject(obj),nomFace1),(App.getDocument(docname).getObject(Point1),'')]
	App.getDocument(docname).getObject(Ligne1).MapMode = 'FaceNormal'
	Gui.Selection.addSelection(str(docname),Ligne1) # on selectionne la ligne pour pouvoir le masquer
	Gui.runCommand('Std_ToggleVisibility',0) #on cache la ligne
	Gui.Selection.clearSelection()
	#
	#### 2eme datum point sur la ligne et le 2e plan
	fpoint2 = App.getDocument(docname).getObject(body.Name).newObject('PartDesign::Point','P2')
	Point2 = str(fpoint2.Name)
	App.getDocument(docname).getObject(Point2).Support = [(App.getDocument(docname).getObject(Ligne1),''),(App.getDocument(docname).getObject(obj),nomFace2)]
	App.getDocument(docname).getObject(Point2).MapMode = 'ProximityPoint1'
	Gui.Selection.addSelection(str(docname),Point2) # on selectionne le point pour pouvoir le masquer
	Gui.runCommand('Std_ToggleVisibility',0) #on cache le point
	Gui.Selection.clearSelection()
	
	### datum plan inertiel selon 2 points
	fplanmilieu = App.getDocument(docname).getObject(body.Name).newObject('PartDesign::Plane','PlanMilieu')
	PlanMilieu = str(fplanmilieu.Name)
	App.getDocument(docname).getObject(PlanMilieu).Support = [(App.getDocument(docname).getObject(Point2), ''), (App.getDocument(docname).getObject(Point1), ''), ]
	App.getDocument(docname).getObject(PlanMilieu).MapMode = 'InertialCS'
	
	### on crée un groupe 'Geometries' s'il n'existe pas
	try :
		nomGroupe = App.ActiveDocument.Geometries.Label
	except :
		nomGroupe = ''
		None
	if nomGroupe == 'Geometries':
		print('Le groupe Geometries existe déjà')
	else :
		groupe = App.activeDocument().Tip = App.activeDocument().addObject('App::DocumentObjectGroup','Geometries')
		nomGroupe = groupe.Label
	
	##### on déplace les géométries de construction dans le groupe
	App.getDocument(docname).getObject(Point1).adjustRelativeLinks(App.getDocument(docname).getObject(nomGroupe))
	App.getDocument(docname).getObject(nomGroupe).addObject(App.getDocument(docname).getObject(Point1))
	App.getDocument(docname).getObject(Ligne1).adjustRelativeLinks(App.getDocument(docname).getObject(nomGroupe))
	App.getDocument(docname).getObject(nomGroupe).addObject(App.getDocument(docname).getObject(Ligne1))
	App.getDocument(docname).getObject(Point2).adjustRelativeLinks(App.getDocument(docname).getObject(nomGroupe))
	App.getDocument(docname).getObject(nomGroupe).addObject(App.getDocument(docname).getObject(Point2))
	App.activeDocument().recompute()

 #### fin des definitions

body = Gui.ActiveDocument.ActiveView.getActiveObject('pdbody') #nom du body

if body == None:
	print('Pas de body actif : activer un body')
	QtGui.QMessageBox.information(None,"","Pas de body actif : activer un body")
else :
	if (Gui.Selection.getSelectionEx() == []): #selection vide
		print('Selectionner 2 faces')
		message()
	else  :
		s, = Gui.Selection.getSelectionEx() #on récupère la selection
		sub = s.SubObjects
		if (len(sub) != 2):
			print('Selectionner exactement 2 faces paralleles')
			message()
		else :
			nomFace1 = s.SubElementNames[0] # on récupère le nom de la 1re face sélectionnée
			nomFace2 = s.SubElementNames[1] # on récupère le nom de la 2e face sélectionnée
			if ((sub[0].ShapeType != 'Face') or (sub[1].ShapeType != 'Face')):
				print('Selectionner seulement des element \"Face\"')
				message()
			else :
				planmilieu()

Gui.Selection.clearSelection()
######################################
Last edited by Grub on Tue Jan 25, 2022 7:53 pm, edited 1 time in total.
Grub
Posts: 303
Joined: Sun Nov 15, 2020 7:28 pm

Re: Comment créer rapidement un plan milieu ?

Post by Grub »

Je suis parti de l'icone de symétrie de PartDesign :
Attachments
PlanMilieu01.JPG
PlanMilieu01.JPG (26.59 KiB) Viewed 1074 times
PlanMilieu01.svg
(69.3 KiB) Downloaded 15 times
Post Reply