QmlDesigner: Implement unimporting bundle materials

Fixes: QDS-7904
Change-Id: I08642c25a2844547d0104a7b3d9fda6afe47cd38
Reviewed-by: <github-actions-qt-creator@cristianadam.eu>
Reviewed-by: Miikka Heikkinen <miikka.heikkinen@qt.io>
This commit is contained in:
Mahmoud Badri
2022-10-12 20:46:17 +03:00
parent 7a967d385e
commit b983b8aa52
12 changed files with 287 additions and 21 deletions

View File

@@ -27,6 +27,8 @@ import QtQuick 2.15
import QtQuick.Layouts 1.15 import QtQuick.Layouts 1.15
import QtQuickDesignerTheme 1.0 import QtQuickDesignerTheme 1.0
import HelperWidgets 2.0 import HelperWidgets 2.0
import QtQuick.Controls
import StudioTheme 1.0 as StudioTheme import StudioTheme 1.0 as StudioTheme
Item { Item {
@@ -43,7 +45,7 @@ Item {
acceptedButtons: Qt.LeftButton | Qt.RightButton acceptedButtons: Qt.LeftButton | Qt.RightButton
onPressed: (mouse) => { onPressed: (mouse) => {
if (mouse.button === Qt.LeftButton) if (mouse.button === Qt.LeftButton && !materialBrowserBundleModel.importerRunning)
rootView.startDragBundleMaterial(modelData, mapToGlobal(mouse.x, mouse.y)) rootView.startDragBundleMaterial(modelData, mapToGlobal(mouse.x, mouse.y))
else if (mouse.button === Qt.RightButton) else if (mouse.button === Qt.RightButton)
root.showContextMenu() root.showContextMenu()
@@ -64,6 +66,48 @@ Item {
anchors.horizontalCenter: parent.horizontalCenter anchors.horizontalCenter: parent.horizontalCenter
source: modelData.bundleMaterialIcon source: modelData.bundleMaterialIcon
cache: false cache: false
Rectangle { // circular indicator for imported bundle materials
width: 10
height: 10
radius: 5
anchors.right: img.right
anchors.top: img.top
anchors.margins: 5
color: "#00ff00"
border.color: "#555555"
border.width: 1
visible: modelData.bundleMaterialImported
ToolTip {
visible: indicatorMouseArea.containsMouse
text: qsTr("Material is imported to project")
delay: 1000
}
MouseArea {
id: indicatorMouseArea
anchors.fill: parent
hoverEnabled: true
}
}
IconButton {
icon: StudioTheme.Constants.plus
tooltip: qsTr("Add an instance to project")
buttonSize: 22
property color c: StudioTheme.Values.themeIconColor
normalColor: Qt.hsla(c.hslHue, c.hslSaturation, c.hslLightness, .2)
hoverColor: Qt.hsla(c.hslHue, c.hslSaturation, c.hslLightness, .3)
pressColor: Qt.hsla(c.hslHue, c.hslSaturation, c.hslLightness, .4)
anchors.right: img.right
anchors.bottom: img.bottom
enabled: !materialBrowserBundleModel.importerRunning
onClicked: {
materialBrowserBundleModel.addToProject(modelData)
}
}
} }
TextInput { TextInput {

View File

@@ -46,8 +46,8 @@ Item {
// Called also from C++ to close context menu on focus out // Called also from C++ to close context menu on focus out
function closeContextMenu() function closeContextMenu()
{ {
cxtMenu.close() ctxMenu.close()
cxtMenuBundle.close() ctxMenuBundle.close()
} }
// Called from C++ to refresh a preview material after it changes // Called from C++ to refresh a preview material after it changes
@@ -79,7 +79,7 @@ Item {
if (!materialBrowserModel.hasMaterialRoot && (!materialBrowserBundleModel.matBundleExists if (!materialBrowserModel.hasMaterialRoot && (!materialBrowserBundleModel.matBundleExists
|| mouse.y < userMatsSecBottom)) { || mouse.y < userMatsSecBottom)) {
root.currentMaterial = null root.currentMaterial = null
cxtMenu.popup() ctxMenu.popup()
} }
} }
} }
@@ -97,8 +97,12 @@ Item {
} }
} }
UnimportBundleMaterialDialog {
id: unimportBundleMaterialDialog
}
StudioControls.Menu { StudioControls.Menu {
id: cxtMenu id: ctxMenu
closePolicy: StudioControls.Menu.CloseOnEscape | StudioControls.Menu.CloseOnPressOutside closePolicy: StudioControls.Menu.CloseOnEscape | StudioControls.Menu.CloseOnPressOutside
@@ -205,7 +209,7 @@ Item {
} }
StudioControls.Menu { StudioControls.Menu {
id: cxtMenuBundle id: ctxMenuBundle
closePolicy: StudioControls.Menu.CloseOnEscape | StudioControls.Menu.CloseOnPressOutside closePolicy: StudioControls.Menu.CloseOnEscape | StudioControls.Menu.CloseOnPressOutside
@@ -224,9 +228,22 @@ Item {
StudioControls.MenuSeparator {} StudioControls.MenuSeparator {}
StudioControls.MenuItem { StudioControls.MenuItem {
text: qsTr("Add to project") enabled: !materialBrowserBundleModel.importerRunning
text: qsTr("Add an instance to project")
onTriggered: materialBrowserBundleModel.addMaterial(root.currentBundleMaterial) onTriggered: {
materialBrowserBundleModel.addToProject(root.currentBundleMaterial)
}
}
StudioControls.MenuItem {
enabled: !materialBrowserBundleModel.importerRunning && root.currentBundleMaterial.bundleMaterialImported
text: qsTr("Remove from project")
onTriggered: {
unimportBundleMaterialDialog.targetBundleMaterial = root.currentBundleMaterial
unimportBundleMaterialDialog.open()
}
} }
} }
@@ -301,13 +318,14 @@ Item {
height: root.height - searchBox.height height: root.height - searchBox.height
clip: true clip: true
visible: materialBrowserModel.hasQuick3DImport && !materialBrowserModel.hasMaterialRoot visible: materialBrowserModel.hasQuick3DImport && !materialBrowserModel.hasMaterialRoot
interactive: !ctxMenu.opened && !ctxMenuBundle.opened
Column { Column {
Section { Section {
id: userMaterialsSection id: userMaterialsSection
width: root.width width: root.width
caption: qsTr("User materials") caption: qsTr("Materials")
hideHeader: !materialBrowserBundleModel.matBundleExists hideHeader: !materialBrowserBundleModel.matBundleExists
Grid { Grid {
@@ -329,7 +347,7 @@ Item {
onShowContextMenu: { onShowContextMenu: {
root.currentMaterial = model root.currentMaterial = model
cxtMenu.popup() ctxMenu.popup()
} }
} }
} }
@@ -392,7 +410,7 @@ Item {
onShowContextMenu: { onShowContextMenu: {
root.currentBundleMaterial = modelData root.currentBundleMaterial = modelData
cxtMenuBundle.popup() ctxMenuBundle.popup()
} }
} }
} }

View File

@@ -0,0 +1,85 @@
/****************************************************************************
**
** Copyright (C) 2022 The Qt Company Ltd.
** Contact: https://www.qt.io/licensing/
**
** This file is part of Qt Creator.
**
** Commercial License Usage
** Licensees holding valid commercial Qt licenses may use this file in
** accordance with the commercial license agreement provided with the
** Software or, alternatively, in accordance with the terms contained in
** a written agreement between you and The Qt Company. For licensing terms
** and conditions see https://www.qt.io/terms-conditions. For further
** information use the contact form at https://www.qt.io/contact-us.
**
** GNU General Public License Usage
** Alternatively, this file may be used under the terms of the GNU
** General Public License version 3 as published by the Free Software
** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
** included in the packaging of this file. Please review the following
** information to ensure the GNU General Public License requirements will
** be met: https://www.gnu.org/licenses/gpl-3.0.html.
**
****************************************************************************/
import QtQuick
import QtQuick.Controls
import QtQuick.Layouts
import QtQuickDesignerTheme
import HelperWidgets
import StudioControls as StudioControls
import StudioTheme as StudioTheme
Dialog {
id: root
title: qsTr("Bundle material might be in use")
anchors.centerIn: parent
closePolicy: Popup.CloseOnEscape
implicitWidth: 300
modal: true
property var targetBundleMaterial
contentItem: Column {
spacing: 20
width: parent.width
Text {
id: folderNotEmpty
text: qsTr("If the material you are removing is in use, it might cause the project to malfunction.\n\nAre you sure you want to remove the material?")
color: StudioTheme.Values.themeTextColor
wrapMode: Text.WordWrap
anchors.right: parent.right
anchors.left: parent.left
leftPadding: 10
rightPadding: 10
Keys.onEnterPressed: btnRemove.onClicked()
Keys.onReturnPressed: btnRemove.onClicked()
}
Row {
anchors.right: parent.right
Button {
id: btnRemove
text: qsTr("Remove")
onClicked: {
materialBrowserBundleModel.removeFromProject(root.targetBundleMaterial)
root.accept()
}
}
Button {
text: qsTr("Cancel")
onClicked: root.reject()
}
}
}
onOpened: folderNotEmpty.forceActiveFocus()
}

View File

@@ -51,6 +51,7 @@ public:
QString importComponent(const QString &qmlFile, QString importComponent(const QString &qmlFile,
const QStringList &files); const QStringList &files);
QString unimportComponent(const QString &qmlFile); QString unimportComponent(const QString &qmlFile);
Utils::FilePath resolveBundleImportPath();
signals: signals:
// The metaInfo parameter will be invalid if an error was encountered during // The metaInfo parameter will be invalid if an error was encountered during
@@ -63,7 +64,6 @@ private:
void handleImportTimer(); void handleImportTimer();
QVariantHash loadAssetRefMap(const Utils::FilePath &bundlePath); QVariantHash loadAssetRefMap(const Utils::FilePath &bundlePath);
void writeAssetRefMap(const Utils::FilePath &bundlePath, const QVariantHash &assetRefMap); void writeAssetRefMap(const Utils::FilePath &bundlePath, const QVariantHash &assetRefMap);
Utils::FilePath resolveBundleImportPath();
Utils::FilePath m_bundleDir; Utils::FilePath m_bundleDir;
QString m_bundleId; QString m_bundleId;

View File

@@ -70,4 +70,20 @@ bool BundleMaterial::visible() const
return m_visible; return m_visible;
} }
bool BundleMaterial::setImported(bool imported)
{
if (m_imported != imported) {
m_imported = imported;
emit materialImportedChanged();
return true;
}
return false;
}
bool BundleMaterial::imported() const
{
return m_imported;
}
} // namespace QmlDesigner } // namespace QmlDesigner

View File

@@ -40,6 +40,7 @@ class BundleMaterial : public QObject
Q_PROPERTY(QString bundleMaterialName MEMBER m_name CONSTANT) Q_PROPERTY(QString bundleMaterialName MEMBER m_name CONSTANT)
Q_PROPERTY(QUrl bundleMaterialIcon MEMBER m_icon CONSTANT) Q_PROPERTY(QUrl bundleMaterialIcon MEMBER m_icon CONSTANT)
Q_PROPERTY(bool bundleMaterialVisible MEMBER m_visible NOTIFY materialVisibleChanged) Q_PROPERTY(bool bundleMaterialVisible MEMBER m_visible NOTIFY materialVisibleChanged)
Q_PROPERTY(bool bundleMaterialImported READ imported WRITE setImported NOTIFY materialImportedChanged)
public: public:
BundleMaterial(QObject *parent, BundleMaterial(QObject *parent,
@@ -57,8 +58,12 @@ public:
QStringList files() const; QStringList files() const;
bool visible() const; bool visible() const;
bool setImported(bool imported);
bool imported() const;
signals: signals:
void materialVisibleChanged(); void materialVisibleChanged();
void materialImportedChanged();
private: private:
QString m_name; QString m_name;
@@ -68,6 +73,7 @@ private:
QStringList m_files; QStringList m_files;
bool m_visible = true; bool m_visible = true;
bool m_imported = false;
}; };
} // namespace QmlDesigner } // namespace QmlDesigner

View File

@@ -37,6 +37,16 @@ void BundleMaterialCategory::addBundleMaterial(BundleMaterial *bundleMat)
m_categoryMaterials.append(bundleMat); m_categoryMaterials.append(bundleMat);
} }
bool BundleMaterialCategory::updateImportedState(const QStringList &importedMats)
{
bool changed = false;
for (BundleMaterial *mat : std::as_const(m_categoryMaterials))
changed |= mat->setImported(importedMats.contains(mat->qml().chopped(4)));
return changed;
}
bool BundleMaterialCategory::filter(const QString &searchText) bool BundleMaterialCategory::filter(const QString &searchText)
{ {
bool visible = false; bool visible = false;

View File

@@ -42,6 +42,7 @@ public:
BundleMaterialCategory(QObject *parent, const QString &name); BundleMaterialCategory(QObject *parent, const QString &name);
void addBundleMaterial(BundleMaterial *bundleMat); void addBundleMaterial(BundleMaterial *bundleMat);
bool updateImportedState(const QStringList &importedMats);
bool filter(const QString &searchText); bool filter(const QString &searchText);
QString name() const; QString name() const;

View File

@@ -122,7 +122,7 @@ void MaterialBrowserBundleModel::loadMaterialBundle()
m_matBundleExists = true; m_matBundleExists = true;
const QString bundleId = m_matBundleObj.value("id").toString(); QString bundleId = m_matBundleObj.value("id").toString();
const QJsonObject catsObj = m_matBundleObj.value("categories").toObject(); const QJsonObject catsObj = m_matBundleObj.value("categories").toObject();
const QStringList categories = catsObj.keys(); const QStringList categories = catsObj.keys();
@@ -160,8 +160,17 @@ void MaterialBrowserBundleModel::loadMaterialBundle()
m_importer = new Internal::BundleImporter(matBundleDir.path(), bundleId, sharedFiles); m_importer = new Internal::BundleImporter(matBundleDir.path(), bundleId, sharedFiles);
connect(m_importer, &Internal::BundleImporter::importFinished, this, [&](const QmlDesigner::NodeMetaInfo &metaInfo) { connect(m_importer, &Internal::BundleImporter::importFinished, this, [&](const QmlDesigner::NodeMetaInfo &metaInfo) {
m_importerRunning = false;
emit importerRunningChanged();
if (metaInfo.isValid()) if (metaInfo.isValid())
emit addBundleMaterialToProjectRequested(metaInfo); emit bundleMaterialImported(metaInfo);
});
connect(m_importer, &Internal::BundleImporter::unimportFinished, this, [&](const QmlDesigner::NodeMetaInfo &metaInfo) {
Q_UNUSED(metaInfo)
m_importerRunning = false;
emit importerRunningChanged();
emit bundleMaterialUnimported(metaInfo);
}); });
} }
@@ -193,6 +202,11 @@ void MaterialBrowserBundleModel::setHasMaterialRoot(bool b)
emit hasMaterialRootChanged(); emit hasMaterialRootChanged();
} }
Internal::BundleImporter *MaterialBrowserBundleModel::bundleImporter() const
{
return m_importer;
}
void MaterialBrowserBundleModel::setSearchText(const QString &searchText) void MaterialBrowserBundleModel::setSearchText(const QString &searchText)
{ {
QString lowerSearchText = searchText.toLower(); QString lowerSearchText = searchText.toLower();
@@ -219,6 +233,16 @@ void MaterialBrowserBundleModel::setSearchText(const QString &searchText)
resetModel(); resetModel();
} }
void MaterialBrowserBundleModel::updateImportedState(const QStringList &importedMats)
{
bool changed = false;
for (BundleMaterialCategory *cat : std::as_const(m_bundleCategories))
changed |= cat->updateImportedState(importedMats);
if (changed)
resetModel();
}
void MaterialBrowserBundleModel::resetModel() void MaterialBrowserBundleModel::resetModel()
{ {
beginResetModel(); beginResetModel();
@@ -230,12 +254,30 @@ void MaterialBrowserBundleModel::applyToSelected(BundleMaterial *mat, bool add)
emit applyToSelectedTriggered(mat, add); emit applyToSelectedTriggered(mat, add);
} }
void MaterialBrowserBundleModel::addMaterial(BundleMaterial *mat) void MaterialBrowserBundleModel::addToProject(BundleMaterial *mat)
{ {
QString err = m_importer->importComponent(mat->qml(), mat->files()); QString err = m_importer->importComponent(mat->qml(), mat->files());
if (!err.isEmpty()) if (err.isEmpty()) {
m_importerRunning = true;
emit importerRunningChanged();
} else {
qWarning() << __FUNCTION__ << err; qWarning() << __FUNCTION__ << err;
}
}
void MaterialBrowserBundleModel::removeFromProject(BundleMaterial *mat)
{
emit bundleMaterialAboutToUnimport(mat->type());
QString err = m_importer->unimportComponent(mat->qml());
if (err.isEmpty()) {
m_importerRunning = true;
emit importerRunningChanged();
} else {
qWarning() << __FUNCTION__ << err;
}
} }
} // namespace QmlDesigner } // namespace QmlDesigner

View File

@@ -50,6 +50,7 @@ class MaterialBrowserBundleModel : public QAbstractListModel
Q_PROPERTY(bool isEmpty MEMBER m_isEmpty NOTIFY isEmptyChanged) Q_PROPERTY(bool isEmpty MEMBER m_isEmpty NOTIFY isEmptyChanged)
Q_PROPERTY(bool hasQuick3DImport READ hasQuick3DImport WRITE setHasQuick3DImport NOTIFY hasQuick3DImportChanged) Q_PROPERTY(bool hasQuick3DImport READ hasQuick3DImport WRITE setHasQuick3DImport NOTIFY hasQuick3DImportChanged)
Q_PROPERTY(bool hasMaterialRoot READ hasMaterialRoot WRITE setHasMaterialRoot NOTIFY hasMaterialRootChanged) Q_PROPERTY(bool hasMaterialRoot READ hasMaterialRoot WRITE setHasMaterialRoot NOTIFY hasMaterialRootChanged)
Q_PROPERTY(bool importerRunning MEMBER m_importerRunning NOTIFY importerRunningChanged)
public: public:
MaterialBrowserBundleModel(QObject *parent = nullptr); MaterialBrowserBundleModel(QObject *parent = nullptr);
@@ -59,6 +60,7 @@ public:
QHash<int, QByteArray> roleNames() const override; QHash<int, QByteArray> roleNames() const override;
void setSearchText(const QString &searchText); void setSearchText(const QString &searchText);
void updateImportedState(const QStringList &importedMats);
bool hasQuick3DImport() const; bool hasQuick3DImport() const;
void setHasQuick3DImport(bool b); void setHasQuick3DImport(bool b);
@@ -66,10 +68,13 @@ public:
bool hasMaterialRoot() const; bool hasMaterialRoot() const;
void setHasMaterialRoot(bool b); void setHasMaterialRoot(bool b);
Internal::BundleImporter *bundleImporter() const;
void resetModel(); void resetModel();
Q_INVOKABLE void applyToSelected(QmlDesigner::BundleMaterial *mat, bool add = false); Q_INVOKABLE void applyToSelected(QmlDesigner::BundleMaterial *mat, bool add = false);
Q_INVOKABLE void addMaterial(QmlDesigner::BundleMaterial *mat); Q_INVOKABLE void addToProject(QmlDesigner::BundleMaterial *mat);
Q_INVOKABLE void removeFromProject(QmlDesigner::BundleMaterial *mat);
signals: signals:
void isEmptyChanged(); void isEmptyChanged();
@@ -77,7 +82,10 @@ signals:
void hasMaterialRootChanged(); void hasMaterialRootChanged();
void materialVisibleChanged(); void materialVisibleChanged();
void applyToSelectedTriggered(QmlDesigner::BundleMaterial *mat, bool add = false); void applyToSelectedTriggered(QmlDesigner::BundleMaterial *mat, bool add = false);
void addBundleMaterialToProjectRequested(const QmlDesigner::NodeMetaInfo &metaInfo); void bundleMaterialImported(const QmlDesigner::NodeMetaInfo &metaInfo);
void bundleMaterialAboutToUnimport(const QmlDesigner::TypeName &type);
void bundleMaterialUnimported(const QmlDesigner::NodeMetaInfo &metaInfo);
void importerRunningChanged();
private: private:
void loadMaterialBundle(); void loadMaterialBundle();
@@ -93,6 +101,7 @@ private:
bool m_hasMaterialRoot = false; bool m_hasMaterialRoot = false;
bool m_matBundleExists = false; bool m_matBundleExists = false;
bool m_probeMatBundleDir = false; bool m_probeMatBundleDir = false;
bool m_importerRunning = false;
}; };
} // namespace QmlDesigner } // namespace QmlDesigner

View File

@@ -27,6 +27,7 @@
#include "bindingproperty.h" #include "bindingproperty.h"
#include "bundlematerial.h" #include "bundlematerial.h"
#include "bundleimporter.h"
#include "materialbrowserwidget.h" #include "materialbrowserwidget.h"
#include "materialbrowsermodel.h" #include "materialbrowsermodel.h"
#include "materialbrowserbundlemodel.h" #include "materialbrowserbundlemodel.h"
@@ -178,13 +179,28 @@ WidgetInfo MaterialBrowserView::widgetInfo()
if (defaultMat.isValid()) if (defaultMat.isValid())
applyBundleMaterialToDropTarget(defaultMat); applyBundleMaterialToDropTarget(defaultMat);
else else
m_widget->materialBrowserBundleModel()->addMaterial(bundleMat); m_widget->materialBrowserBundleModel()->addToProject(bundleMat);
}); });
connect(matBrowserBundleModel, &MaterialBrowserBundleModel::addBundleMaterialToProjectRequested, this, connect(matBrowserBundleModel, &MaterialBrowserBundleModel::bundleMaterialImported, this,
[&] (const QmlDesigner::NodeMetaInfo &metaInfo) { [&] (const QmlDesigner::NodeMetaInfo &metaInfo) {
applyBundleMaterialToDropTarget({}, metaInfo); applyBundleMaterialToDropTarget({}, metaInfo);
updateBundleMaterialsImportedState();
}); });
connect(matBrowserBundleModel, &MaterialBrowserBundleModel::bundleMaterialAboutToUnimport, this,
[&] (const QmlDesigner::TypeName &type) {
// delete instances of the bundle material that is about to be unimported
executeInTransaction("MaterialBrowserView::widgetInfo", [&] {
Utils::reverseForeach(m_widget->materialBrowserModel()->materials(), [&](const ModelNode &mat) {
if (mat.isValid() && mat.type() == type)
QmlObjectNode(mat).destroy();
});
});
});
connect(matBrowserBundleModel, &MaterialBrowserBundleModel::bundleMaterialUnimported, this,
&MaterialBrowserView::updateBundleMaterialsImportedState);
} }
return createWidgetInfo(m_widget.data(), return createWidgetInfo(m_widget.data(),
@@ -273,6 +289,7 @@ void MaterialBrowserView::modelAttached(Model *model)
m_widget->materialBrowserModel()->setHasMaterialRoot(rootModelNode().isSubclassOf("QtQuick3D.Material")); m_widget->materialBrowserModel()->setHasMaterialRoot(rootModelNode().isSubclassOf("QtQuick3D.Material"));
m_hasQuick3DImport = model->hasImport("QtQuick3D"); m_hasQuick3DImport = model->hasImport("QtQuick3D");
updateBundleMaterialsImportedState();
// Project load is already very busy and may even trigger puppet reset, so let's wait a moment // Project load is already very busy and may even trigger puppet reset, so let's wait a moment
// before refreshing the model // before refreshing the model
@@ -440,6 +457,22 @@ void QmlDesigner::MaterialBrowserView::loadPropertyGroups()
m_propertyGroupsLoaded = m_widget->materialBrowserModel()->loadPropertyGroups(matPropsPath); m_propertyGroupsLoaded = m_widget->materialBrowserModel()->loadPropertyGroups(matPropsPath);
} }
void MaterialBrowserView::updateBundleMaterialsImportedState()
{
using namespace Utils;
QStringList importedBundleMats;
FilePath materialBundlePath = m_widget->materialBrowserBundleModel()->bundleImporter()->resolveBundleImportPath();
if (materialBundlePath.exists()) {
importedBundleMats = transform(materialBundlePath.dirEntries({{"*.qml"}, QDir::Files}),
[](const FilePath &f) { return f.fileName().chopped(4); });
}
m_widget->materialBrowserBundleModel()->updateImportedState(importedBundleMats);
}
ModelNode MaterialBrowserView::getBundleMaterialDefaultInstance(const TypeName &type) ModelNode MaterialBrowserView::getBundleMaterialDefaultInstance(const TypeName &type)
{ {
const QList<ModelNode> materials = m_widget->materialBrowserModel()->materials(); const QList<ModelNode> materials = m_widget->materialBrowserModel()->materials();
@@ -505,7 +538,7 @@ void MaterialBrowserView::customNotification(const AbstractView *view, const QSt
if (defaultMat.isValid()) if (defaultMat.isValid())
applyBundleMaterialToDropTarget(defaultMat); applyBundleMaterialToDropTarget(defaultMat);
else else
m_widget->materialBrowserBundleModel()->addMaterial(m_draggedBundleMaterial); m_widget->materialBrowserBundleModel()->addToProject(m_draggedBundleMaterial);
m_draggedBundleMaterial = nullptr; m_draggedBundleMaterial = nullptr;
} }

View File

@@ -68,6 +68,7 @@ private:
void refreshModel(bool updateImages); void refreshModel(bool updateImages);
bool isMaterial(const ModelNode &node) const; bool isMaterial(const ModelNode &node) const;
void loadPropertyGroups(); void loadPropertyGroups();
void updateBundleMaterialsImportedState();
void applyBundleMaterialToDropTarget(const ModelNode &bundleMat, const NodeMetaInfo &metaInfo = {}); void applyBundleMaterialToDropTarget(const ModelNode &bundleMat, const NodeMetaInfo &metaInfo = {});
ModelNode getBundleMaterialDefaultInstance(const TypeName &type); ModelNode getBundleMaterialDefaultInstance(const TypeName &type);
@@ -75,6 +76,7 @@ private:
QList<ModelNode> m_bundleMaterialTargets; QList<ModelNode> m_bundleMaterialTargets;
QList<ModelNode> m_selectedModels; // selected 3D model nodes QList<ModelNode> m_selectedModels; // selected 3D model nodes
BundleMaterial *m_draggedBundleMaterial = nullptr; BundleMaterial *m_draggedBundleMaterial = nullptr;
bool m_bundleMaterialAddToSelected = false; bool m_bundleMaterialAddToSelected = false;
bool m_hasQuick3DImport = false; bool m_hasQuick3DImport = false;
bool m_autoSelectModelMaterial = false; // TODO: wire this to some action bool m_autoSelectModelMaterial = false; // TODO: wire this to some action