3d in Python

Description: Программирование на супер модном мега крутом языке Питон.

dyvniy M
Topic author, Администратор
Администратор
Avatar
dyvniy M
Topic author, Администратор
Администратор
Age: 37
Reputation: 1
Loyalty: 1
Posts: 3345
Joined: Wed, 10 Oct 2012
With us: 7 years 8 months
Профессия: Программист
Location: Россия, Москва
ICQ Website Skype VK

#1by dyvniy » Mon, 20 Jan 2020, 16:26:11

https://habr.com/ru/post/411899/
Spoiler
Как создавать 3d модели с помощью Python
3D-принтеры
Привет, Хабр! Однажды мне потребовалось создать 3D модель дна, подробнее в этой статье. Сегодня я хочу рассказать о том, как можно создавать 3D модели Python 3. Способов для этого достаточно много: blender python api, Vpython… Но я хочу рассказать, как делать модели используя только Python.



→ Ссылка на Github

STL

Для этого нужно понять, как работает формат stl (популярный формат 3D файлов).
Вся модель в этом формате состоит из множества треугольников, поэтому файл состоит из 3-х мерных координат их вершин.

STL-файл
Пример

Я хотел бы показать, как реализовать создание 3D модели по яркостям пикселей на фотографии. Я взял вот это фото снизу.



Изображение обрабатывается (немного размывается, чтобы не было резких скачков яркости) с помощью библиотеки opencv.

import cv2
import numpy as np

cd_1=['0', '0', '0']# создание массива для хранения координат 1 вершины
cd_2=['0', '0', '0']# создание массива для хранения координат 2 вершины
cd_3=['0', '0', '0']# создание массива для хранения координат 3 вершины

file_stl='new.stl'
file_im=r'C:\Users\allex\Pictures\2.jpg'# путь к изображению
op_stl=open(file_stl, 'w')
op_im=cv2.imread(file_im)

gray = cv2.cvtColor(op_im, cv2.COLOR_BGR2GRAY)#преобразование в чб изображение
blur = cv2.GaussianBlur(gray,(0,0),1)# небольшое размытие для сглажеввания шумов
res=cv2.resize(blur,(320,240))# преобразование изображения к размеру 320*240

Снизу функция, принимающая 3 массива с координатами вершин треугольника и записывающая в файл 1 треугольную грань.


def face_file_stl(cd_1, cd_2, cd_3):
op_stl.write("facet normal 0 0 0")
op_stl.write("outer loop")
op_stl.write("vertex " + " ".join(cd_1))#запись в файл координаты 1 вершины
op_stl.write("vertex " + " ".join(cd_2))#запись в файл координаты 2 вершины
op_stl.write("vertex " + " ".join(cd_3))#запись в файл координаты 3 вершины
op_stl.write("endloop \n\tendfacet")

Теперь самое главное — создание правильных координат вершин треугольников из которых состоит 3D модель.


Часть кода, создающая координаты.


for i in range(size.shape[1]):#перебор пикселей по ширине

for k in range(size.shape[0]-1):#перебор пикселей по высоте

if i!=size.shape[1]-1:

try: #making the first triangls for relief
cd_1=[str(i), str(k), str(blur[k, i]) ]
cd_2=[str(i + 1), str(k), str(blur[k, i+1]) ]
cd_3=[str(i+1), str(k+1), str(blur[k+1,i+1])]

except:
print('er')

face_file_stl(cd_1, cd_2, cd_3)

try: #making the second triangls for relief
cd_1=[str(i), str(k), str(blur[k, i]) ]
cd_2=[str(i+1), str(k+1), str(blur[k+1, i+1])]
cd_3=[str(i), str(k+1), str(blur[k+1,i]) ]
except:
print('er')

face_file_stl(cd_1, cd_2, cd_3)

Созданная 3D модель
Собственно, это все, что я хотел написать до следующей статьи.

Весь код
import cv2
cd_1=['0', '0', '0']# создание массива для хранения координат 1 вершины
cd_2=['0', '0', '0']# создание массива для хранения координат 2 вершины
cd_3=['0', '0', '0']# создание массива для хранения координат 3 вершины
file_stl='new.stl'
file_im=r'C:\Users\allex\Pictures\22.jpg'# путь к изображению
op_stl=open(file_stl, 'w')
op_im=cv2.imread(file_im)

gray = cv2.cvtColor(op_im, cv2.COLOR_BGR2GRAY)#преобразование в чб изображение
blur = cv2.GaussianBlur(gray,(0,0),1)# небольшое размытие для сглажеввания шумов
blur=cv2.resize(blur,(320,240))
x=0
y=0
file='STL_project-1.stl'
o_1="\n\t"
o_2="\n\t\t"
o_3="\n\t\t\t"
op_stl.write("solid")
def face_file_stl(cd_1, cd_2, cd_3):
op_stl.write(o_1+"facet normal 0 0 0")
op_stl.write(o_2 + "outer loop")
op_stl.write(o_3 + "vertex " + " ".join(cd_1))#запись в файл координаты 1 вершины
op_stl.write(o_3 + "vertex " + " ".join(cd_2))#запись в файл координаты 2 вершины
op_stl.write(o_3 + "vertex " + " ".join(cd_3))#запись в файл координаты 3 вершины
op_stl.write(o_2 + "endloop \n\tendfacet")

#making the first triangls for base
for i in range(blur.shape[1]-1):
cd_1=[str(i),"0","0"]
cd_3=[str(i+1),str(blur.shape[0]-1),"0"]
cd_2=[str(i),str(blur.shape[0]-1),"0"]
face_file_stl(cd_1, cd_2, cd_3)
#making the second triangls for base
for i in range(blur.shape[1]-1):
cd_1=[str(i+1),str(blur.shape[0]-1),"0"]
cd_3=[str(i),"0","0"]
cd_2=[str(i+1),"0","0"]
face_file_stl(cd_1, cd_2, cd_3)
#base has done

for i in range(blur.shape[1]):
if i%30==0:
print(i)
for k in range(blur.shape[0]-1):#making the first triangls for relief
if i!=blur.shape[1]-1:
try:

cd_1=[str(i), str(k), str(blur[k, i]) ]
cd_2=[str(i + 1), str(k), str(blur[k, i+1]) ]
cd_3=[str(i+1), str(k+1), str(blur[k+1,i+1])]

except:
print('er')
face_file_stl(cd_1, cd_2, cd_3)
#for j in range(blur.shape[1]-1):#making the second triangls for relief
try:
cd_1=[str(i), str(k), str(blur[k, i]) ]
cd_2=[str(i+1),str(k+1), str(blur[k+1, i+1])]
cd_3=[str(i), str(k+1), str(blur[k+1,i]) ]
except:
print('er')
face_file_stl(cd_1, cd_2, cd_3)
#relief has done

#making the first triangls for right side
for i in range(blur.shape[1]):
if i!=blur.shape[1]-1:
try:
cd_1=[str(i),str(blur.shape[0]-1),"0"]
cd_3=[str(i+1),str(blur.shape[0]-1),str(blur[blur.shape[0]-1, i+1])]
cd_2=[str(i),str(blur.shape[0]-1),str(blur[blur.shape[0]-1, i])]

except:
print("er")
face_file_stl(cd_1, cd_2, cd_3)

#making the second triangls for right side
try:
cd_1=[str(i),str(blur.shape[0]-1),"0"]
cd_3=[str(i+1),str(blur.shape[0]-1),"0"]
cd_2=[str(i+1),str(blur.shape[0]-1),str(blur[blur.shape[0]-1, i+1])]
except:
print("er")
face_file_stl(cd_1, cd_2, cd_3)

if i!=blur.shape[1]-1:
try:
cd_1=[str(i),'0',"0"]
cd_2=[str(i+1),'0',str(blur[0, i+1])]
cd_3=[str(i),'0',str(blur[0, i])]

except:
print("er")
face_file_stl(cd_1, cd_2, cd_3)

#making the second triangls for right side
try:
cd_1=[str(i),'0',"0"]
cd_2=[str(i+1),'0',"0"]
cd_3=[str(i+1),'0',str(blur[0, i+1])]
except:
print("er")
face_file_stl(cd_1, cd_2, cd_3)

for i in range(blur.shape[0]):
if i!=blur.shape[0]-1:
try:
cd_1=['0',str(i),"0"]
cd_3=['0',str(i+1),str(blur[ i+1,0])]
cd_2=['0',str(i),str(blur[i,0])]

except:
print("er")
face_file_stl(cd_1, cd_2, cd_3)

#making the second triangls for right side
try:
cd_1=['0',str(i),"0"]
cd_3=['0',str(i+1),"0"]
cd_2=['0',str(i+1),str(blur[i+1,0])]
except:
print("er")
face_file_stl(cd_1, cd_2, cd_3)

try:
cd_2=[str(blur.shape[1]-1),str(i),"0"]
cd_3=[str(blur.shape[1]-1),str(i+1),str(blur[ i+1,blur.shape[1]-1])]
cd_1=[str(blur.shape[1]-1),str(i),str(blur[i,blur.shape[1]-1])]

except:
print("er")
face_file_stl(cd_1, cd_2, cd_3)

#making the second triangls for right side
try:
cd_2=[str(blur.shape[1]-1),str(i),"0"]
cd_3=[str(blur.shape[1]-1),str(i+1),"0"]
cd_1=[str(blur.shape[1]-1),str(i+1),str(blur[i+1,blur.shape[1]-1])]
except:
print("er")

face_file_stl(cd_1, cd_2, cd_3)

op_stl.write("\nendsolid" )
op_stl.close()

print('end')
Image

Forum name: Python
Description: Программирование на супер модном мега крутом языке Питон.

Quick reply


Enter the code exactly as it appears. All letters are case insensitive.
Confirmation code
:) ;) :hihi: :P :hah: :haha: :angel: :( :st: :_( :cool: 8-| :beee: :ham: :rrr: :grr: :* :secret: :stupid: :music: View more smilies
   

Return to “Python”

Who is online (over the past 15 minutes)

Users browsing this forum: 1 guest