[recovery mode] Расширение (плагин) SketchUp для проектирования мебели программистом
При расчете стоимости новой кухни цена оказалась такой большой, что я решил сделать её сам так как это обойдется в два раза дешевле. Для тренировки решил сделать для себя рабочий стол. Достаточно быстро пришло понимание: чтобы сделать хорошую вещь нужно сделать 3D модель. Это позволит на этапе проектирования посмотреть как будет выглядеть мебель и продумать как в дальнейшем будет происходить сборка. Так как 3D моделированием я не занимаюсь, то начал искать программу попроще. И самая простая что нашел SketchUp. При создании модели постоянно приходилось править модель из-за постоянно изменявшихся размеров. И после третьего изменения появилась идея — сделать параметризированную модель, чтобы она сама генерировалась с нужными размерами. SketchUp поддерживает скрипты на языке Ruby и эта статья о том что у меня получилось.
Решение достаточно простое — создаю некоторый API, который позволяет создавать 3D объекты листов ЛПСД с нужными параметрами. Из этих объектов компонуется готовая модель, а также в отдельный файл выгружаются размеры листов для передачи их в центр распила. В результате эксплуатации добавил ещё возможность указывать кромки для листов. Данный плагин был использован для проектирования более десятка различных изделий из ЛДСП. С каждым новым проектом плагин дорабатывался и модифицировался, улучшалось удобство и совершенствовалось API. В качестве примера последний проект — стол-тумба. На картинке модель + готовое изделие (птица и собака для привлечения внимания :))
Красные — это 2 м кромки, фиолетовый — кромки 0.4 мм. Нижние полки не до конца, так как там батарея отопления у стены. Столешница отстает от стены на 4 см чтобы тепло от батарее отопления поднималось вверх и обогревало стену (вообще делать мебель самому очень удобно — можно сделать под свои размеры).
# Толщина фанеры
$weght = 16.0
# Зазор между ящиком и задней стенкой
$zazor = 5.0
# Отступ от краев для ящика
$dWidth = 26.0
#
$width = 770
$offsetStena = 40
$dStoledhnica = 20
$height = 2500 - 150 - 900
$depthLeft = 600
$depthRight = $depthLeft - 175
$jshikHeight = 200
$heightPlanka = 300
$heightJshik = 190
$heightJshikOffset = 10
# Функция точки входа
def object3D_main()
# Загрузить библиотеки
Shasoft::Object3D::loadLibrary()
# Установить толщину ЛДСП
Shasoft::Object3D::LDSP::setWeght($weght)
# Создать модель
stenaLeft = Shasoft::Object3D::LDSP::create($height-$weght,$depthLeft,"2 0 0 1").name("Левая стена").rotateY(-90)
stenaRight = Shasoft::Object3D::LDSP::create($height-$weght,$depthLeft,"2 0 0 1").name("Правая стена").rotateY(-90).moveX($width-$weght)
stoleshnica = Shasoft::Object3D::LDSP::create($width,$depthLeft+$dStoledhnica-$offsetStena,"2 2 1 2").name("Столешница").move(-$weght,-$dStoledhnica,$height-$weght)
polka1 = Shasoft::Object3D::LDSP::create($width-$weght*2,$depthRight,"2 0 0 0").name("Полка 1").moveZ(400)
polka2 = Shasoft::Object3D::LDSP::create($width-$weght*2,$depthRight-$weght,"2 0 0 0").name("Полка 2").moveZ(600)
polka3 = Shasoft::Object3D::LDSP::create($width-$weght*2,$depthLeft-$offsetStena,"2 0 0 0").name("Полка 3").moveZ(800+$heightJshik+$heightJshikOffset+10-$weght-5)
pereborka1 = Shasoft::Object3D::LDSP::create($width-$weght*2,$heightPlanka).name("Переборка").rotateX(90).moveY($depthRight).moveZ(400+$weght)
# Верхний ящик
jshik1box = Shasoft::Object3D::LDSP::create_box($width-$weght*2-$dWidth,$depthLeft-$zazor-$offsetStena,$heightJshik,"Верхний ящик",1).moveX($dWidth/2).moveZ($height-$heightJshik-$heightJshikOffset-$weght)
jshik1Fasad = Shasoft::Object3D::LDSP::create($width,200,"2 2 2 2").rotateX(90).moveX(-$weght).moveZ($height-$heightJshik-$heightJshikOffset-$weght-5).name("Фасад ящика 1")
jshik1 = Shasoft::Object3D::create(jshik1box,jshik1Fasad)
# Нижний ящик
jshik2box = Shasoft::Object3D::LDSP::create_box($width-$weght*2-$dWidth,$depthLeft-$zazor-$offsetStena,$heightJshik-$weght-5,"Нижний ящик",1).moveX($dWidth/2).moveZ($height-$heightJshik-$heightJshikOffset-$weght)
jshik2Fasad = Shasoft::Object3D::LDSP::create($width,200,"2 2 2 2").rotateX(90).moveX(-$weght).moveZ($height-$heightJshik-$heightJshikOffset-$weght-5).name("Фасад ящика 2")
jshik2 = Shasoft::Object3D::create(jshik2box,jshik2Fasad).moveZ(-$height+800+$heightJshik+$heightJshikOffset+$weght+10)
# Двери
widthDver = $width/2-5
dver1 = Shasoft::Object3D::LDSP::create(widthDver,800-5-10,"2 2 2 2").rotateX(90).moveZ(5).moveX(-$weght).name("Дверь 1")
dver2 = dver1.copy.moveX($width-widthDver).name("Дверь 2")
#
for i in 0..5
Shasoft::Object3D::LDSP::create(467,247,"0 2 0 0").name("Полка в шкаф").moveX(-600).moveZ(i*50)
end
for i in 0..2
Shasoft::Object3D::LDSP::create(467,640,"0 2 0 0").name("Полка в шкаф 2").moveX(-600-600).moveZ(i*50)
end
#
Shasoft::Object3D::LDSP::write_csv( File.dirname(__FILE__)+"/main.csv" )
#Shasoft::Object3D::LDSP::write_csv_cut( File.dirname(__FILE__)+"/cut.csv" )
#Shasoft::Object3D::show()
end
Скачиваем файл Object3D.rbz
Запускаем SketchUp
Открываем Диспечер расширений (Окно/Диспечер расширений)
Жмем кнопку «Установить расширение» и выбираем скаченный файл Object3D.rbz
После этого плагин запрашивает директорию где будут храниться проекты. Т.е. выводится окно «Укажите директорию с проектами» и требуется указать папку где вы будете хранить ваши проекты.
В результате у нас появляется наше расширение
Переходим в папку которую мы указали для хранения проектов. Эту папку можно изменить в меню плагина
Создаем в папке директорию с названием нашего проекта. В моем случае это «Шкафчик в зал». Затем заходим в созданную директорию и создаем файл main.rb в котором создаем функцию точки входа
# Функция точки входа
def object3D_main()
... # код для генерации модели
end
Перезапускаем SketchUp и в меню плагина у вас появится пункт с названием созданной вами папки. Теперь вы выборе этого пункта будет происходить следующее:
- очистка консоли Ruby
- удаление всех элементов в текущем проекте
- загрузка файла main.rb из указанной директории
- вызов функции object3D_main
В функции object3D_main нужно сделать генерацию вашей модели. Можно скопировать в файл main.rb код который я приводил выше и тогда у вас сгенерируется мой шкафчик.
Файл «core.rb»
Каждая функция возвращает объект Shasoft: Object3D: Object3D который содержит методы для перемещения объекта и его поворота
-
Функция name() — установка имени объекта. Не стоит им пренебрегать. При сборке может сильно помочь :)
-
Функции объекта moveX, moveY, moveZ позволяют перемещать объект по соответствующим осям.
-
Функция move(x, y, z) позволяет переместить объект сразу по трем осям
-
Функции объекта rotateX, rotateY, rotateZ позволяют вращать объект вокруг соответствующих осей.
-
Есть функции псевдонимы moveRed, moveGreen, moveBlue, rotateRed, rotateGreen, rotateBlue где оси X (red), Y (green), Z (blue) названы по их цвету в SketchUp. Может кому-то так будет удобнее.
Каждая функция возвращает указатель на сам обхект. Это позволяет делать цепочку вызовов# Повернем объект на 90 градусов вокруг оси X и переместим по оси Y на 100 мм obj.rotateX(90).moveY(100)
-
Функция объекта set(dict, key, value) позволяет установить значение атрибута. dict — имя словаря, key — имя атрибута, value — значение
-
Функция объекта get(dict, key, value=nil) позволяет получить значение атрибута. dict — имя словаря, key — имя атрибута, value — значение
-
Метод copy позволяет получить копию объекта (хотя работает не очень стабильно :))
-
Метод group позволяет получить стандартный объект SketchUp: Group
Определен метод для создания объекта. В качестве параметров можно передавать список объектов Shasoft: Object3D: Object3D или SketchUp: Group. Если список параметров пустой, то будет создана новая группа
# Создать объект со списком дочерних объектов
Shasoft::Object3D::create(*args)
Также есть функция которая позволяет получить список объектов (Skechup: Group). Можно задать имя словаря и будут возвращены только объекты, у которых такой словарь присутствует. В частности именно так я отделяю объекты лист ЛПСД от других. При создании я устанавливаю словарь LDSP по которому потом и фильтрую все объекты сцены.
# Получить список объектов
# dict - имя словаря
Shasoft::Object3D::get(dict=nil)
Файл »2D_weght»
# Создать 3D объект выдавливания
# pts - список точек в координатной плоскости x,y
# weght - толщина(высота)
Shasoft::Object3D::create_pushpull(pts,weght)
# Создать плоскую поверхность с заданной толщиной
# lX - размер по X
# lY - размер по Y
# weght - толщина
Shasoft::Object3D::create_plane(lX,lY,weght)
Файл «ldsp.rb»
# Получить текущую толщину
Shasoft::Object3D::LDSP::weght
# Установить толщину
Shasoft::Object3D::LDSP::setWeght(weght)
# Получить текущий материал ЛДСП
Shasoft::Object3D::LDSP::material
# Установить материал ЛДСП
Shasoft::Object3D::LDSP::setMaterial(material)
# Создать лист ЛДСП
# width - ширина (по X)
# depth - глубина (по Y)
# kromka - кромка [X ближний, Y левый, X дальний, Y правый], 0 - нет кромки, 1 - кромка 0.4 мм, 2 - кромка 2 мм
Shasoft::Object3D::LDSP::create(width,depth,kromka="0 0 0 0")
Вспомогательная функция для создания выдвижных ящиков
# Создать ящик
# width - ширина
# depth - глубина
# height - высота
# name - имя
# is_kromka - 1/0 кромить верх 2 мм кромкой
Shasoft::Object3D::LDSP::create_box(width,depth,height,name,is_kromka)
результат работы
# Записать размеры в файл CSV
Shasoft::Object3D::LDSP::write_csv(filepath)
в результате будет сгенерирован следующий csv файл со следующими колонками
- A — Ширина
- B — Глубина
- C Количество деталей
- D — кромки в формате Д-длинная сторона, К-короткая сторона. Именно в таком их записывают в той конторе в которой я заказываю распил деталей. Возможно это стандарт.
- E — кромки в том формате в котором вы их задавили при генерации
- F — Название всех деталей. Это полезно при сборке
В заключении
Проектирование и сборка мебели самому — это экономия денег где-то в 2 раза. А также возможность втиснуть ваше индивидуальное мебельное изделие в любую нестандартную дырку в квартире. Я обычно собираю мебель на конфирматах 7×50 из ЛДСП 16 мм
При наличии сверла для конфирматов
(и небольшого навыка) сборка занимает не так много времени.
Единственный минус — в это можно втянуться. После рабочего стола я уже собрал: кухню, несколько клеток (для одной и той же птицы она на фото), полки (навесные и напольные), тумбы и столы. В общем «захламил» в квартире все неиспользуемые места.
Ссылка для скачивания расширения
Ссылка на страницу плагина