Перейти к содержимому
davidka.net > 💻 🧠 Код 1001 > 📚 Учебные Материалы > FreeCAD > Создание аддонов для FreeCAD > Урок 5. Сохранение и загрузка настроек

Урок 5. Сохранение и загрузка настроек

  • автор:

📘 Учебный курс: Создание аддонов для FreeCAD

Цель урока: сделать так, чтобы аддон «Box Builder» запоминал последние введённые размеры и восстанавливал их при следующем запуске.


💾 Часть 1. Как FreeCAD хранит настройки?

FreeCAD предоставляет встроенный механизм для хранения пользовательских параметров — через Parameter Manager.

Он работает с иерархической базой параметров, похожей на Windows Registry.

Основные методы:

# Получить группу параметров
params = FreeCAD.ParamGet("User parameter:BaseApp/Preferences/MyAddon")

# Сохранить значение
params.SetFloat("LastLength", 30.0)
params.SetString("LastName", "MyBox")

# Загрузить значение (с значением по умолчанию)
length = params.GetFloat("LastLength", 10.0)  # 10.0 — если нет такого параметра
name = params.GetString("LastName", "DefaultBox")

💡 Путь "User parameter:BaseApp/Preferences/..." — стандартное место для пользовательских настроек.


🛠 Часть 2. Обновлённый аддон: «Box Builder с памятью»

Мы модифицируем предыдущий аддон, добавив сохранение и загрузку последних значений.

Файл box_builder_workbench.py (обновлённая версия)

# box_builder_workbench.py
import FreeCAD, FreeCADGui
from PySide import QtGui, QtCore

# === ПУТЬ К НАСТРОЙКАМ ===
PARAM_PATH = "User parameter:BaseApp/Preferences/BoxBuilderAddon"

def get_saved_settings():
    """Загружает сохранённые настройки или возвращает значения по умолчанию"""
    params = FreeCAD.ParamGet(PARAM_PATH)
    return {
        "length": params.GetFloat("LastLength", 30.0),
        "width": params.GetFloat("LastWidth", 20.0),
        "height": params.GetFloat("LastHeight", 10.0),
        "name": params.GetString("LastName", "CustomBox")
    }

def save_settings(length, width, height, name):
    """Сохраняет текущие настройки"""
    params = FreeCAD.ParamGet(PARAM_PATH)
    params.SetFloat("LastLength", length)
    params.SetFloat("LastWidth", width)
    params.SetFloat("LastHeight", height)
    params.SetString("LastName", name)


# === ФУНКЦИЯ СОЗДАНИЯ КОРОБКИ ===
def create_box(length, width, height, name="CustomBox"):
    doc = FreeCAD.ActiveDocument
    if not doc:
        doc = FreeCAD.newDocument("BoxBuilder")

    # Уникальное имя
    base_name = name
    index = 1
    obj_name = base_name
    while obj_name in [obj.Name for obj in doc.Objects]:
        obj_name = f"{base_name}_{index}"
        index += 1

    box = doc.addObject("Part::Box", obj_name)
    box.Length = length
    box.Width = width
    box.Height = height
    doc.recompute()
    return box


# === ДИАЛОГОВОЕ ОКНО ===
class BoxBuilderDialog(QtGui.QDialog):
    def __init__(self):
        super(BoxBuilderDialog, self).__init__()
        self.setWindowTitle("Box Builder")
        self.setWindowFlags(QtCore.Qt.WindowStaysOnTopHint)
        self.resize(300, 180)

        # Загружаем сохранённые настройки
        settings = get_saved_settings()

        # Поля ввода
        self.length_input = QtGui.QLineEdit(str(settings["length"]))
        self.width_input = QtGui.QLineEdit(str(settings["width"]))
        self.height_input = QtGui.QLineEdit(str(settings["height"]))
        self.name_input = QtGui.QLineEdit(settings["name"])

        # Кнопки
        self.create_button = QtGui.QPushButton("Create Box")
        self.cancel_button = QtGui.QPushButton("Cancel")

        # Подключение
        self.create_button.clicked.connect(self.on_create)
        self.cancel_button.clicked.connect(self.reject)

        # Раскладка
        layout = QtGui.QFormLayout()
        layout.addRow("Name:", self.name_input)
        layout.addRow("Length (mm):", self.length_input)
        layout.addRow("Width (mm):", self.width_input)
        layout.addRow("Height (mm):", self.height_input)

        button_layout = QtGui.QHBoxLayout()
        button_layout.addWidget(self.create_button)
        button_layout.addWidget(self.cancel_button)

        main_layout = QtGui.QVBoxLayout()
        main_layout.addLayout(layout)
        main_layout.addLayout(button_layout)
        self.setLayout(main_layout)

    def on_create(self):
        try:
            name = self.name_input.text().strip()
            if not name:
                name = "CustomBox"

            length = float(self.length_input.text())
            width = float(self.width_input.text())
            height = float(self.height_input.text())

            if length <= 0 or width <= 0 or height <= 0:
                raise ValueError("All dimensions must be positive")

            # Создаём объект
            create_box(length, width, height, name)

            # Сохраняем настройки
            save_settings(length, width, height, name)

            self.accept()

        except ValueError as e:
            QtGui.QMessageBox.warning(self, "Input Error", f"Invalid input:\n{str(e)}")


# === КОМАНДА И РАБОЧАЯ СРЕДА (без изменений) ===
class BoxBuilderCommand:
    def GetResources(self):
        return {"MenuText": "Box Builder", "ToolTip": "Create a box with custom dimensions"}
    def Activated(self):
        dialog = BoxBuilderDialog()
        dialog.exec_()
    def IsActive(self):
        return True

class BoxBuilderWorkbench(FreeCADGui.Workbench):
    MenuText = "Box Builder"
    ToolTip = "Create custom boxes with GUI"
    def Initialize(self):
        self.list = ["BoxBuilderCommand"]
        self.appendToolbar("Box Tools", self.list)
        self.appendMenu("Box Builder", self.list)
    def GetClassName(self):
        return "Gui::PythonWorkbench"

FreeCADGui.addCommand("BoxBuilderCommand", BoxBuilderCommand())

🔍 Что изменилось?

  1. Добавлены функции:
  • get_saved_settings() — загружает последние значения
  • save_settings() — сохраняет текущие
  1. Путь к параметрам:
   PARAM_PATH = "User parameter:BaseApp/Preferences/BoxBuilderAddon"

→ Все настройки хранятся в отдельной группе, не мешая другим аддонам.

  1. Поле для имени добавлено в интерфейс.
  2. При запуске окна — поля заполняются сохранёнными значениями.
  3. После создания — текущие значения сохраняются автоматически.

▶️ Проверка работы

  1. Запустите FreeCAD
  2. Откройте Box Builder
  3. Введите, например:
  • Name: MyTestBox
  • Length: 50
  • Width: 30
  • Height: 20
  1. Нажмите Create Box
  2. Закройте FreeCAD
  3. Запустите снова
  4. Откройте Box Builder

✅ Поля должны быть заполнены теми же значениями!


📂 Где хранятся эти настройки?

  • Windows: в реестре (HKEY_CURRENT_USER\SOFTWARE\FreeCAD\...)
  • Linux/macOS: в файле user.cfg внутри папки FreeCAD

Но вам не нужно знать это — FreeCAD сам управляет хранением.


🧪 Практическое задание

  1. Добавьте галочку «Center on origin» и сохраняйте её состояние между запусками.
  2. Сделайте так, чтобы при первом запуске аддона использовались разумные значения по умолчанию (уже реализовано).
  3. Добавьте кнопку «Reset to defaults», которая сбрасывает поля на значения по умолчанию и очищает сохранённые настройки.

Подсказка для сброса:

def reset_settings():
    params = FreeCAD.ParamGet(PARAM_PATH)
    params.RemGroup("BoxBuilderAddon")  # Удаляет всю группу

💡 Советы

  • Всегда указывайте значение по умолчанию в GetFloat(), GetString() и т.д.
  • Не сохраняйте слишком много — только то, что реально нужно пользователю
  • Используйте уникальный путь (BoxBuilderAddon), чтобы не конфликтовать с другими аддонами

▶️ Что дальше?

В Уроке 6 мы:

  • Добавим иконки к кнопкам и рабочей среде
  • Научимся использовать SVG и PNG в интерфейсе
  • Сделаем аддон визуально привлекательным

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *