Apply webkit style clang format on code base
parent
73f0404c2e
commit
57b1a802f3
|
@ -1,18 +1,18 @@
|
|||
#include <QOpenGLFunctions>
|
||||
#include <QTextEdit>
|
||||
#include <QVBoxLayout>
|
||||
#include <QOpenGLFunctions>
|
||||
|
||||
#include "about_widget.h"
|
||||
#include "version.h"
|
||||
#include "model_widget.h"
|
||||
#include "version.h"
|
||||
|
||||
AboutWidget::AboutWidget()
|
||||
{
|
||||
QTextEdit *versionInfoLabel = new QTextEdit;
|
||||
QTextEdit* versionInfoLabel = new QTextEdit;
|
||||
versionInfoLabel->setText(QString("%1 %2 (version: %3 build: %4 %5)\nopengl: %6 shader: %7 core: %8").arg(APP_NAME).arg(APP_HUMAN_VER).arg(APP_VER).arg(__DATE__).arg(__TIME__).arg(ModelWidget::m_openGLVersion).arg(ModelWidget::m_openGLShadingLanguageVersion).arg(ModelWidget::m_openGLIsCoreProfile ? "true" : "false"));
|
||||
versionInfoLabel->setReadOnly(true);
|
||||
|
||||
QVBoxLayout *mainLayout = new QVBoxLayout;
|
||||
QVBoxLayout* mainLayout = new QVBoxLayout;
|
||||
mainLayout->addWidget(versionInfoLabel);
|
||||
|
||||
setLayout(mainLayout);
|
||||
|
|
|
@ -3,8 +3,7 @@
|
|||
|
||||
#include <QDialog>
|
||||
|
||||
class AboutWidget : public QDialog
|
||||
{
|
||||
class AboutWidget : public QDialog {
|
||||
Q_OBJECT
|
||||
public:
|
||||
AboutWidget();
|
||||
|
|
|
@ -1,9 +1,9 @@
|
|||
#include <QtGlobal>
|
||||
#include <QMatrix4x4>
|
||||
#include <QDebug>
|
||||
#include <cmath>
|
||||
#include <QtMath>
|
||||
#include "ccd_ik_resolver.h"
|
||||
#include <QDebug>
|
||||
#include <QMatrix4x4>
|
||||
#include <QtGlobal>
|
||||
#include <QtMath>
|
||||
#include <cmath>
|
||||
|
||||
CcdIkSolver::CcdIkSolver()
|
||||
{
|
||||
|
@ -15,9 +15,9 @@ void CcdIkSolver::setSolveFrom(int fromNodeIndex)
|
|||
}
|
||||
|
||||
void CcdIkSolver::setNodeHingeConstraint(int nodeIndex,
|
||||
const QVector3D &axis, double minLimitDegrees, double maxLimitDegrees)
|
||||
const QVector3D& axis, double minLimitDegrees, double maxLimitDegrees)
|
||||
{
|
||||
auto &node = m_nodes[nodeIndex];
|
||||
auto& node = m_nodes[nodeIndex];
|
||||
node.axis = axis;
|
||||
node.minLimitDegrees = minLimitDegrees;
|
||||
node.maxLimitDegrees = maxLimitDegrees;
|
||||
|
@ -33,7 +33,7 @@ void CcdIkSolver::setDistanceThreshod(float threshold)
|
|||
m_distanceThreshold2 = threshold * threshold;
|
||||
}
|
||||
|
||||
int CcdIkSolver::addNodeInOrder(const QVector3D &position)
|
||||
int CcdIkSolver::addNodeInOrder(const QVector3D& position)
|
||||
{
|
||||
CcdIkNode node;
|
||||
node.position = position;
|
||||
|
@ -42,13 +42,13 @@ int CcdIkSolver::addNodeInOrder(const QVector3D &position)
|
|||
return nodeCount;
|
||||
}
|
||||
|
||||
void CcdIkSolver::solveTo(const QVector3D &position)
|
||||
void CcdIkSolver::solveTo(const QVector3D& position)
|
||||
{
|
||||
//qDebug() << "solveTo:" << position;
|
||||
m_destination = position;
|
||||
float lastDistance2 = 0;
|
||||
for (int i = 0; i < m_maxRound; i++) {
|
||||
const auto &endEffector = m_nodes[m_nodes.size() - 1];
|
||||
const auto& endEffector = m_nodes[m_nodes.size() - 1];
|
||||
float distance2 = (endEffector.position - m_destination).lengthSquared();
|
||||
//qDebug() << "Round:" << i << " distance2:" << distance2;
|
||||
if (distance2 <= m_distanceThreshold2)
|
||||
|
@ -60,7 +60,7 @@ void CcdIkSolver::solveTo(const QVector3D &position)
|
|||
}
|
||||
}
|
||||
|
||||
const QVector3D &CcdIkSolver::getNodeSolvedPosition(int index)
|
||||
const QVector3D& CcdIkSolver::getNodeSolvedPosition(int index)
|
||||
{
|
||||
Q_ASSERT(index >= 0 && index < (int)m_nodes.size());
|
||||
return m_nodes[index].position;
|
||||
|
@ -82,18 +82,18 @@ float CcdIkSolver::angleInRangle360BetweenTwoVectors(QVector3D a, QVector3D b, Q
|
|||
|
||||
void CcdIkSolver::iterate()
|
||||
{
|
||||
auto rotateChildren = [&](const QQuaternion &quaternion, int i) {
|
||||
const auto &origin = m_nodes[i];
|
||||
auto rotateChildren = [&](const QQuaternion& quaternion, int i) {
|
||||
const auto& origin = m_nodes[i];
|
||||
for (size_t j = i + 1; j <= m_nodes.size() - 1; j++) {
|
||||
auto &next = m_nodes[j];
|
||||
auto& next = m_nodes[j];
|
||||
const auto offset = next.position - origin.position;
|
||||
next.position = origin.position + quaternion.rotatedVector(offset);
|
||||
}
|
||||
};
|
||||
|
||||
for (int i = m_nodes.size() - 2; i >= m_fromNodeIndex; i--) {
|
||||
const auto &origin = m_nodes[i];
|
||||
const auto &endEffector = m_nodes[m_nodes.size() - 1];
|
||||
const auto& origin = m_nodes[i];
|
||||
const auto& endEffector = m_nodes[m_nodes.size() - 1];
|
||||
QVector3D from = (endEffector.position - origin.position).normalized();
|
||||
QVector3D to = (m_destination - origin.position).normalized();
|
||||
auto quaternion = QQuaternion::rotationTo(from, to);
|
||||
|
@ -111,12 +111,10 @@ void CcdIkSolver::iterate()
|
|||
int childIndex = i + 1;
|
||||
if (childIndex >= m_nodes.size())
|
||||
continue;
|
||||
const auto &parent = m_nodes[parentIndex];
|
||||
const auto &child = m_nodes[childIndex];
|
||||
QVector3D angleFrom = (QVector3D(0.0, parent.position.y(), parent.position.z()) -
|
||||
QVector3D(0.0, origin.position.y(), origin.position.z())).normalized();
|
||||
QVector3D angleTo = (QVector3D(0.0, child.position.y(), child.position.z()) -
|
||||
QVector3D(0.0, origin.position.y(), origin.position.z())).normalized();
|
||||
const auto& parent = m_nodes[parentIndex];
|
||||
const auto& child = m_nodes[childIndex];
|
||||
QVector3D angleFrom = (QVector3D(0.0, parent.position.y(), parent.position.z()) - QVector3D(0.0, origin.position.y(), origin.position.z())).normalized();
|
||||
QVector3D angleTo = (QVector3D(0.0, child.position.y(), child.position.z()) - QVector3D(0.0, origin.position.y(), origin.position.z())).normalized();
|
||||
float degrees = angleInRangle360BetweenTwoVectors(angleFrom, angleTo, QVector3D(1.0, 0.0, 0.0));
|
||||
if (degrees < origin.minLimitDegrees) {
|
||||
auto quaternion = QQuaternion::fromAxisAndAngle(QVector3D(1.0, 0.0, 0.0), origin.minLimitDegrees - degrees);
|
||||
|
|
|
@ -1,31 +1,30 @@
|
|||
#ifndef DUST3D_APPLICATION_CCD_IK_SOLVER_H_
|
||||
#define DUST3D_APPLICATION_CCD_IK_SOLVER_H_
|
||||
|
||||
#include <vector>
|
||||
#include <QVector3D>
|
||||
#include <QQuaternion>
|
||||
#include <QVector3D>
|
||||
#include <vector>
|
||||
|
||||
struct CcdIkNode
|
||||
{
|
||||
struct CcdIkNode {
|
||||
QVector3D position;
|
||||
QVector3D axis;
|
||||
double minLimitDegrees;
|
||||
double maxLimitDegrees;
|
||||
};
|
||||
|
||||
class CcdIkSolver
|
||||
{
|
||||
class CcdIkSolver {
|
||||
public:
|
||||
CcdIkSolver();
|
||||
void setMaxRound(int maxRound);
|
||||
void setDistanceThreshod(float threshold);
|
||||
int addNodeInOrder(const QVector3D &position);
|
||||
void solveTo(const QVector3D &position);
|
||||
const QVector3D &getNodeSolvedPosition(int index);
|
||||
int addNodeInOrder(const QVector3D& position);
|
||||
void solveTo(const QVector3D& position);
|
||||
const QVector3D& getNodeSolvedPosition(int index);
|
||||
int getNodeCount();
|
||||
void setNodeHingeConstraint(int nodeIndex,
|
||||
const QVector3D &axis, double minLimitDegrees, double maxLimitDegrees);
|
||||
const QVector3D& axis, double minLimitDegrees, double maxLimitDegrees);
|
||||
void setSolveFrom(int fromNodeIndex);
|
||||
|
||||
private:
|
||||
float angleInRangle360BetweenTwoVectors(QVector3D a, QVector3D b, QVector3D planeNormal);
|
||||
void iterate();
|
||||
|
|
|
@ -1,13 +1,13 @@
|
|||
#include <QAbstractListModel>
|
||||
#include <dust3d/base/debug.h>
|
||||
#include "component_list_model.h"
|
||||
#include "document.h"
|
||||
#include <QAbstractListModel>
|
||||
#include <dust3d/base/debug.h>
|
||||
|
||||
ComponentListModel::ComponentListModel(const Document *document, QObject *parent):
|
||||
QAbstractListModel(parent),
|
||||
m_document(document)
|
||||
ComponentListModel::ComponentListModel(const Document* document, QObject* parent)
|
||||
: QAbstractListModel(parent)
|
||||
, m_document(document)
|
||||
{
|
||||
connect(m_document, &Document::componentPreviewPixmapChanged, [this](const dust3d::Uuid &componentId) {
|
||||
connect(m_document, &Document::componentPreviewPixmapChanged, [this](const dust3d::Uuid& componentId) {
|
||||
auto findIndex = this->m_componentIdToIndexMap.find(componentId);
|
||||
if (findIndex != this->m_componentIdToIndexMap.end()) {
|
||||
//dust3dDebug << "dataChanged:" << findIndex->second.row();
|
||||
|
@ -18,7 +18,7 @@ ComponentListModel::ComponentListModel(const Document *document, QObject *parent
|
|||
this->setListingComponentId(dust3d::Uuid());
|
||||
this->reload();
|
||||
});
|
||||
connect(m_document, &Document::componentChildrenChanged, [this](const dust3d::Uuid &componentId) {
|
||||
connect(m_document, &Document::componentChildrenChanged, [this](const dust3d::Uuid& componentId) {
|
||||
if (componentId != this->listingComponentId())
|
||||
return;
|
||||
this->reload();
|
||||
|
@ -29,7 +29,7 @@ void ComponentListModel::reload()
|
|||
{
|
||||
beginResetModel();
|
||||
m_componentIdToIndexMap.clear();
|
||||
const SkeletonComponent *listingComponent = m_document->findComponent(m_listingComponentId);
|
||||
const SkeletonComponent* listingComponent = m_document->findComponent(m_listingComponentId);
|
||||
if (nullptr != listingComponent) {
|
||||
for (int i = 0; i < (int)listingComponent->childrenIds.size(); ++i) {
|
||||
m_componentIdToIndexMap[listingComponent->childrenIds[i]] = createIndex(i, 0);
|
||||
|
@ -39,7 +39,7 @@ void ComponentListModel::reload()
|
|||
emit layoutChanged();
|
||||
}
|
||||
|
||||
QModelIndex ComponentListModel::componentIdToIndex(const dust3d::Uuid &componentId) const
|
||||
QModelIndex ComponentListModel::componentIdToIndex(const dust3d::Uuid& componentId) const
|
||||
{
|
||||
auto findIndex = m_componentIdToIndexMap.find(componentId);
|
||||
if (findIndex == m_componentIdToIndexMap.end())
|
||||
|
@ -47,34 +47,34 @@ QModelIndex ComponentListModel::componentIdToIndex(const dust3d::Uuid &component
|
|||
return findIndex->second;
|
||||
}
|
||||
|
||||
int ComponentListModel::rowCount(const QModelIndex &parent) const
|
||||
int ComponentListModel::rowCount(const QModelIndex& parent) const
|
||||
{
|
||||
if (parent.isValid())
|
||||
return 0;
|
||||
const SkeletonComponent *listingComponent = m_document->findComponent(m_listingComponentId);
|
||||
const SkeletonComponent* listingComponent = m_document->findComponent(m_listingComponentId);
|
||||
if (nullptr == listingComponent)
|
||||
return 0;
|
||||
return (int)listingComponent->childrenIds.size();
|
||||
}
|
||||
|
||||
int ComponentListModel::columnCount(const QModelIndex &parent) const
|
||||
int ComponentListModel::columnCount(const QModelIndex& parent) const
|
||||
{
|
||||
if (parent.isValid())
|
||||
return 0;
|
||||
return 1;
|
||||
}
|
||||
|
||||
const SkeletonComponent *ComponentListModel::modelIndexToComponent(const QModelIndex &index) const
|
||||
const SkeletonComponent* ComponentListModel::modelIndexToComponent(const QModelIndex& index) const
|
||||
{
|
||||
const SkeletonComponent *listingComponent = m_document->findComponent(m_listingComponentId);
|
||||
const SkeletonComponent* listingComponent = m_document->findComponent(m_listingComponentId);
|
||||
if (nullptr == listingComponent)
|
||||
return nullptr;
|
||||
if (index.row() >= (int)listingComponent->childrenIds.size()) {
|
||||
dust3dDebug << "Component list row is out of range, size:" << listingComponent->childrenIds.size() << "row:" << index.row();
|
||||
return nullptr;
|
||||
}
|
||||
const auto &componentId = listingComponent->childrenIds[index.row()];
|
||||
const SkeletonComponent *component = m_document->findComponent(componentId);
|
||||
const auto& componentId = listingComponent->childrenIds[index.row()];
|
||||
const SkeletonComponent* component = m_document->findComponent(componentId);
|
||||
if (nullptr == component) {
|
||||
dust3dDebug << "Component not found:" << componentId.toString();
|
||||
return nullptr;
|
||||
|
@ -82,50 +82,48 @@ const SkeletonComponent *ComponentListModel::modelIndexToComponent(const QModelI
|
|||
return component;
|
||||
}
|
||||
|
||||
const dust3d::Uuid ComponentListModel::modelIndexToComponentId(const QModelIndex &index) const
|
||||
const dust3d::Uuid ComponentListModel::modelIndexToComponentId(const QModelIndex& index) const
|
||||
{
|
||||
const SkeletonComponent *listingComponent = m_document->findComponent(m_listingComponentId);
|
||||
const SkeletonComponent* listingComponent = m_document->findComponent(m_listingComponentId);
|
||||
if (nullptr == listingComponent)
|
||||
return dust3d::Uuid();
|
||||
if (index.row() >= (int)listingComponent->childrenIds.size()) {
|
||||
dust3dDebug << "Component list row is out of range, size:" << listingComponent->childrenIds.size() << "row:" << index.row();
|
||||
return dust3d::Uuid();
|
||||
}
|
||||
const auto &componentId = listingComponent->childrenIds[index.row()];
|
||||
const auto& componentId = listingComponent->childrenIds[index.row()];
|
||||
return componentId;
|
||||
}
|
||||
|
||||
QVariant ComponentListModel::data(const QModelIndex &index, int role) const
|
||||
QVariant ComponentListModel::data(const QModelIndex& index, int role) const
|
||||
{
|
||||
switch (role) {
|
||||
case Qt::ToolTipRole: {
|
||||
const SkeletonComponent *component = modelIndexToComponent(index);
|
||||
if (nullptr != component) {
|
||||
return component->name;
|
||||
}
|
||||
const SkeletonComponent* component = modelIndexToComponent(index);
|
||||
if (nullptr != component) {
|
||||
return component->name;
|
||||
}
|
||||
break;
|
||||
} break;
|
||||
case Qt::DecorationRole: {
|
||||
const SkeletonComponent *component = modelIndexToComponent(index);
|
||||
if (nullptr != component) {
|
||||
if (0 == component->previewPixmap.width()) {
|
||||
static QPixmap s_emptyPixmap;
|
||||
if (0 == s_emptyPixmap.width()) {
|
||||
QImage image((int)Theme::partPreviewImageSize, (int)Theme::partPreviewImageSize, QImage::Format_ARGB32);
|
||||
image.fill(Qt::transparent);
|
||||
s_emptyPixmap = QPixmap::fromImage(image);
|
||||
}
|
||||
return s_emptyPixmap;
|
||||
const SkeletonComponent* component = modelIndexToComponent(index);
|
||||
if (nullptr != component) {
|
||||
if (0 == component->previewPixmap.width()) {
|
||||
static QPixmap s_emptyPixmap;
|
||||
if (0 == s_emptyPixmap.width()) {
|
||||
QImage image((int)Theme::partPreviewImageSize, (int)Theme::partPreviewImageSize, QImage::Format_ARGB32);
|
||||
image.fill(Qt::transparent);
|
||||
s_emptyPixmap = QPixmap::fromImage(image);
|
||||
}
|
||||
return component->previewPixmap;
|
||||
return s_emptyPixmap;
|
||||
}
|
||||
return component->previewPixmap;
|
||||
}
|
||||
break;
|
||||
} break;
|
||||
}
|
||||
return QVariant();
|
||||
}
|
||||
|
||||
void ComponentListModel::setListingComponentId(const dust3d::Uuid &componentId)
|
||||
void ComponentListModel::setListingComponentId(const dust3d::Uuid& componentId)
|
||||
{
|
||||
if (m_listingComponentId == componentId)
|
||||
return;
|
||||
|
|
|
@ -1,32 +1,33 @@
|
|||
#ifndef DUST3D_APPLICATION_COMPONENT_LIST_MODEL_H_
|
||||
#define DUST3D_APPLICATION_COMPONENT_LIST_MODEL_H_
|
||||
|
||||
#include <unordered_map>
|
||||
#include <dust3d/base/uuid.h>
|
||||
#include <QAbstractListModel>
|
||||
#include <dust3d/base/uuid.h>
|
||||
#include <unordered_map>
|
||||
|
||||
class Document;
|
||||
class SkeletonComponent;
|
||||
|
||||
class ComponentListModel: public QAbstractListModel
|
||||
{
|
||||
class ComponentListModel : public QAbstractListModel {
|
||||
Q_OBJECT
|
||||
signals:
|
||||
void listingComponentChanged(const dust3d::Uuid &componentId);
|
||||
void listingComponentChanged(const dust3d::Uuid& componentId);
|
||||
|
||||
public:
|
||||
ComponentListModel(const Document *document, QObject *parent=nullptr);
|
||||
int rowCount(const QModelIndex &parent = QModelIndex()) const;
|
||||
int columnCount(const QModelIndex &parent = QModelIndex()) const;
|
||||
QVariant data(const QModelIndex &index, int role) const;
|
||||
const SkeletonComponent *modelIndexToComponent(const QModelIndex &index) const;
|
||||
QModelIndex componentIdToIndex(const dust3d::Uuid &componentId) const;
|
||||
const dust3d::Uuid modelIndexToComponentId(const QModelIndex &index) const;
|
||||
ComponentListModel(const Document* document, QObject* parent = nullptr);
|
||||
int rowCount(const QModelIndex& parent = QModelIndex()) const;
|
||||
int columnCount(const QModelIndex& parent = QModelIndex()) const;
|
||||
QVariant data(const QModelIndex& index, int role) const;
|
||||
const SkeletonComponent* modelIndexToComponent(const QModelIndex& index) const;
|
||||
QModelIndex componentIdToIndex(const dust3d::Uuid& componentId) const;
|
||||
const dust3d::Uuid modelIndexToComponentId(const QModelIndex& index) const;
|
||||
const dust3d::Uuid listingComponentId() const;
|
||||
public slots:
|
||||
void setListingComponentId(const dust3d::Uuid &componentId);
|
||||
void setListingComponentId(const dust3d::Uuid& componentId);
|
||||
void reload();
|
||||
|
||||
private:
|
||||
const Document *m_document = nullptr;
|
||||
const Document* m_document = nullptr;
|
||||
dust3d::Uuid m_listingComponentId;
|
||||
std::unordered_map<dust3d::Uuid, QModelIndex> m_componentIdToIndexMap;
|
||||
};
|
||||
|
|
|
@ -1,23 +1,23 @@
|
|||
#include <memory>
|
||||
#include "component_preview_grid_widget.h"
|
||||
#include "component_list_model.h"
|
||||
#include "document.h"
|
||||
#include <memory>
|
||||
|
||||
ComponentPreviewGridWidget::ComponentPreviewGridWidget(Document *document, QWidget *parent):
|
||||
PreviewGridView(parent),
|
||||
m_document(document)
|
||||
ComponentPreviewGridWidget::ComponentPreviewGridWidget(Document* document, QWidget* parent)
|
||||
: PreviewGridView(parent)
|
||||
, m_document(document)
|
||||
{
|
||||
m_componentListModel = std::make_unique<ComponentListModel>(m_document);
|
||||
setModel(m_componentListModel.get());
|
||||
|
||||
connect(this, &ComponentPreviewGridWidget::doubleClicked, [this](const QModelIndex &index) {
|
||||
const SkeletonComponent *component = this->componentListModel()->modelIndexToComponent(index);
|
||||
connect(this, &ComponentPreviewGridWidget::doubleClicked, [this](const QModelIndex& index) {
|
||||
const SkeletonComponent* component = this->componentListModel()->modelIndexToComponent(index);
|
||||
if (nullptr == component)
|
||||
return;
|
||||
if (component->childrenIds.empty()) {
|
||||
std::vector<dust3d::Uuid> partIds;
|
||||
this->m_document->collectComponentDescendantParts(component->id, partIds);
|
||||
for (const auto &partId: partIds)
|
||||
for (const auto& partId : partIds)
|
||||
emit this->selectPartOnCanvas(partId);
|
||||
} else {
|
||||
this->componentListModel()->setListingComponentId(component->id);
|
||||
|
@ -25,17 +25,17 @@ ComponentPreviewGridWidget::ComponentPreviewGridWidget(Document *document, QWidg
|
|||
});
|
||||
}
|
||||
|
||||
ComponentListModel *ComponentPreviewGridWidget::componentListModel()
|
||||
ComponentListModel* ComponentPreviewGridWidget::componentListModel()
|
||||
{
|
||||
return m_componentListModel.get();
|
||||
}
|
||||
|
||||
std::vector<const SkeletonComponent *> ComponentPreviewGridWidget::getSelectedComponents() const
|
||||
std::vector<const SkeletonComponent*> ComponentPreviewGridWidget::getSelectedComponents() const
|
||||
{
|
||||
std::vector<const SkeletonComponent *> components;
|
||||
std::vector<const SkeletonComponent*> components;
|
||||
QModelIndexList selected = selectionModel()->selectedIndexes();
|
||||
for (const auto &it: selected) {
|
||||
const auto &component = m_componentListModel->modelIndexToComponent(it);
|
||||
for (const auto& it : selected) {
|
||||
const auto& component = m_componentListModel->modelIndexToComponent(it);
|
||||
if (nullptr == component)
|
||||
continue;
|
||||
components.push_back(component);
|
||||
|
@ -47,8 +47,8 @@ std::vector<dust3d::Uuid> ComponentPreviewGridWidget::getSelectedComponentIds()
|
|||
{
|
||||
std::vector<dust3d::Uuid> componentIds;
|
||||
QModelIndexList selected = selectionModel()->selectedIndexes();
|
||||
for (const auto &it: selected) {
|
||||
const auto &componentId = m_componentListModel->modelIndexToComponentId(it);
|
||||
for (const auto& it : selected) {
|
||||
const auto& componentId = m_componentListModel->modelIndexToComponentId(it);
|
||||
if (componentId.isNull())
|
||||
continue;
|
||||
componentIds.push_back(componentId);
|
||||
|
@ -60,7 +60,7 @@ std::vector<dust3d::Uuid> ComponentPreviewGridWidget::getSelectedPartIds() const
|
|||
{
|
||||
auto selectedComponents = getSelectedComponents();
|
||||
std::vector<dust3d::Uuid> partIds;
|
||||
for (const auto &component: selectedComponents) {
|
||||
for (const auto& component : selectedComponents) {
|
||||
if (component->linkToPartId.isNull())
|
||||
continue;
|
||||
partIds.push_back(component->linkToPartId);
|
||||
|
|
|
@ -1,30 +1,31 @@
|
|||
#ifndef DUST3D_APPLICATION_COMPONENT_PREVIEW_GRID_WIDGET_H_
|
||||
#define DUST3D_APPLICATION_COMPONENT_PREVIEW_GRID_WIDGET_H_
|
||||
|
||||
#include <memory>
|
||||
#include <dust3d/base/uuid.h>
|
||||
#include <QAbstractListModel>
|
||||
#include "preview_grid_view.h"
|
||||
#include "component_list_model.h"
|
||||
#include "preview_grid_view.h"
|
||||
#include <QAbstractListModel>
|
||||
#include <dust3d/base/uuid.h>
|
||||
#include <memory>
|
||||
|
||||
class Document;
|
||||
class SkeletonComponent;
|
||||
|
||||
class ComponentPreviewGridWidget: public PreviewGridView
|
||||
{
|
||||
class ComponentPreviewGridWidget : public PreviewGridView {
|
||||
Q_OBJECT
|
||||
signals:
|
||||
void unselectAllOnCanvas();
|
||||
void selectPartOnCanvas(const dust3d::Uuid &partId);
|
||||
void selectPartOnCanvas(const dust3d::Uuid& partId);
|
||||
|
||||
public:
|
||||
ComponentPreviewGridWidget(Document *document, QWidget *parent=nullptr);
|
||||
ComponentListModel *componentListModel();
|
||||
std::vector<const SkeletonComponent *> getSelectedComponents() const;
|
||||
ComponentPreviewGridWidget(Document* document, QWidget* parent = nullptr);
|
||||
ComponentListModel* componentListModel();
|
||||
std::vector<const SkeletonComponent*> getSelectedComponents() const;
|
||||
std::vector<dust3d::Uuid> getSelectedComponentIds() const;
|
||||
std::vector<dust3d::Uuid> getSelectedPartIds() const;
|
||||
|
||||
private:
|
||||
std::unique_ptr<ComponentListModel> m_componentListModel;
|
||||
Document *m_document = nullptr;
|
||||
Document* m_document = nullptr;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
#include <dust3d/base/debug.h>
|
||||
#include <QPainter>
|
||||
#include "theme.h"
|
||||
#include "component_preview_images_decorator.h"
|
||||
#include "theme.h"
|
||||
#include <QPainter>
|
||||
#include <dust3d/base/debug.h>
|
||||
|
||||
ComponentPreviewImagesDecorator::ComponentPreviewImagesDecorator(std::unique_ptr<std::vector<PreviewInput>> previewInputs)
|
||||
{
|
||||
|
@ -21,7 +21,7 @@ void ComponentPreviewImagesDecorator::decorate()
|
|||
m_resultImages = std::make_unique<std::unordered_map<dust3d::Uuid, std::unique_ptr<QImage>>>();
|
||||
|
||||
QPointF iconOffset(Theme::previewIconMargin, 0);
|
||||
for (auto &it: *m_previewInputs) {
|
||||
for (auto& it : *m_previewInputs) {
|
||||
if (it.isDirectory) {
|
||||
QPainter painter(it.image.get());
|
||||
painter.setRenderHints(QPainter::Antialiasing);
|
||||
|
|
|
@ -1,17 +1,15 @@
|
|||
#ifndef DUST3D_APPLICATION_COMPONENT_PREVIEW_IMAGES_DECORATOR_H_
|
||||
#define DUST3D_APPLICATION_COMPONENT_PREVIEW_IMAGES_DECORATOR_H_
|
||||
|
||||
#include <QImage>
|
||||
#include <dust3d/base/uuid.h>
|
||||
#include <memory>
|
||||
#include <unordered_map>
|
||||
#include <dust3d/base/uuid.h>
|
||||
#include <QImage>
|
||||
|
||||
class ComponentPreviewImagesDecorator: public QObject
|
||||
{
|
||||
class ComponentPreviewImagesDecorator : public QObject {
|
||||
Q_OBJECT
|
||||
public:
|
||||
struct PreviewInput
|
||||
{
|
||||
struct PreviewInput {
|
||||
dust3d::Uuid id;
|
||||
std::unique_ptr<QImage> image;
|
||||
bool isDirectory = false;
|
||||
|
@ -23,6 +21,7 @@ signals:
|
|||
void finished();
|
||||
public slots:
|
||||
void process();
|
||||
|
||||
private:
|
||||
std::unique_ptr<std::vector<PreviewInput>> m_previewInputs;
|
||||
std::unique_ptr<std::unordered_map<dust3d::Uuid, std::unique_ptr<QImage>>> m_resultImages;
|
||||
|
|
|
@ -1,41 +1,41 @@
|
|||
#include <unordered_set>
|
||||
#include <QVBoxLayout>
|
||||
#include <QHBoxLayout>
|
||||
#include <QPushButton>
|
||||
#include "component_property_widget.h"
|
||||
#include "document.h"
|
||||
#include "float_number_widget.h"
|
||||
#include "theme.h"
|
||||
#include <QColorDialog>
|
||||
#include <QGroupBox>
|
||||
#include "component_property_widget.h"
|
||||
#include "float_number_widget.h"
|
||||
#include "document.h"
|
||||
#include "theme.h"
|
||||
#include <QHBoxLayout>
|
||||
#include <QPushButton>
|
||||
#include <QVBoxLayout>
|
||||
#include <unordered_set>
|
||||
|
||||
ComponentPropertyWidget::ComponentPropertyWidget(Document *document,
|
||||
const std::vector<dust3d::Uuid> &componentIds,
|
||||
QWidget *parent):
|
||||
QWidget(parent),
|
||||
m_document(document),
|
||||
m_componentIds(componentIds)
|
||||
ComponentPropertyWidget::ComponentPropertyWidget(Document* document,
|
||||
const std::vector<dust3d::Uuid>& componentIds,
|
||||
QWidget* parent)
|
||||
: QWidget(parent)
|
||||
, m_document(document)
|
||||
, m_componentIds(componentIds)
|
||||
{
|
||||
preparePartIds();
|
||||
m_color = lastColor();
|
||||
|
||||
QPushButton *colorPreviewArea = new QPushButton;
|
||||
QPushButton* colorPreviewArea = new QPushButton;
|
||||
colorPreviewArea->setStyleSheet("QPushButton {background-color: " + m_color.name() + "; border-radius: 0;}");
|
||||
colorPreviewArea->setFixedSize(Theme::toolIconSize * 1.8, Theme::toolIconSize);
|
||||
|
||||
QPushButton *colorPickerButton = new QPushButton(QChar(fa::eyedropper));
|
||||
QPushButton* colorPickerButton = new QPushButton(QChar(fa::eyedropper));
|
||||
Theme::initIconButton(colorPickerButton);
|
||||
connect(colorPickerButton, &QPushButton::clicked, this, &ComponentPropertyWidget::showColorDialog);
|
||||
|
||||
QHBoxLayout *colorLayout = new QHBoxLayout;
|
||||
QHBoxLayout* colorLayout = new QHBoxLayout;
|
||||
colorLayout->addWidget(colorPreviewArea);
|
||||
colorLayout->addWidget(colorPickerButton);
|
||||
colorLayout->addStretch();
|
||||
colorLayout->setSizeConstraint(QLayout::SetFixedSize);
|
||||
|
||||
QGroupBox *deformGroupBox = nullptr;
|
||||
QGroupBox* deformGroupBox = nullptr;
|
||||
if (nullptr != m_part) {
|
||||
FloatNumberWidget *thicknessWidget = new FloatNumberWidget;
|
||||
FloatNumberWidget* thicknessWidget = new FloatNumberWidget;
|
||||
thicknessWidget->setItemName(tr("Thickness"));
|
||||
thicknessWidget->setRange(0, 2);
|
||||
thicknessWidget->setValue(m_part->deformThickness);
|
||||
|
@ -45,7 +45,7 @@ ComponentPropertyWidget::ComponentPropertyWidget(Document *document,
|
|||
emit groupOperationAdded();
|
||||
});
|
||||
|
||||
FloatNumberWidget *widthWidget = new FloatNumberWidget;
|
||||
FloatNumberWidget* widthWidget = new FloatNumberWidget;
|
||||
widthWidget->setItemName(tr("Width"));
|
||||
widthWidget->setRange(0, 2);
|
||||
widthWidget->setValue(m_part->deformWidth);
|
||||
|
@ -55,7 +55,7 @@ ComponentPropertyWidget::ComponentPropertyWidget(Document *document,
|
|||
emit groupOperationAdded();
|
||||
});
|
||||
|
||||
QPushButton *thicknessEraser = new QPushButton(QChar(fa::eraser));
|
||||
QPushButton* thicknessEraser = new QPushButton(QChar(fa::eraser));
|
||||
Theme::initIconButton(thicknessEraser);
|
||||
|
||||
connect(thicknessEraser, &QPushButton::clicked, [=]() {
|
||||
|
@ -63,7 +63,7 @@ ComponentPropertyWidget::ComponentPropertyWidget(Document *document,
|
|||
emit groupOperationAdded();
|
||||
});
|
||||
|
||||
QPushButton *widthEraser = new QPushButton(QChar(fa::eraser));
|
||||
QPushButton* widthEraser = new QPushButton(QChar(fa::eraser));
|
||||
Theme::initIconButton(widthEraser);
|
||||
|
||||
connect(widthEraser, &QPushButton::clicked, [=]() {
|
||||
|
@ -71,16 +71,16 @@ ComponentPropertyWidget::ComponentPropertyWidget(Document *document,
|
|||
emit groupOperationAdded();
|
||||
});
|
||||
|
||||
QVBoxLayout *deformLayout = new QVBoxLayout;
|
||||
QVBoxLayout* deformLayout = new QVBoxLayout;
|
||||
|
||||
QHBoxLayout *thicknessLayout = new QHBoxLayout;
|
||||
QHBoxLayout *widthLayout = new QHBoxLayout;
|
||||
QHBoxLayout* thicknessLayout = new QHBoxLayout;
|
||||
QHBoxLayout* widthLayout = new QHBoxLayout;
|
||||
thicknessLayout->addWidget(thicknessEraser);
|
||||
thicknessLayout->addWidget(thicknessWidget);
|
||||
widthLayout->addWidget(widthEraser);
|
||||
widthLayout->addWidget(widthWidget);
|
||||
|
||||
QCheckBox *deformUnifyStateBox = new QCheckBox();
|
||||
QCheckBox* deformUnifyStateBox = new QCheckBox();
|
||||
Theme::initCheckbox(deformUnifyStateBox);
|
||||
deformUnifyStateBox->setText(tr("Unified"));
|
||||
deformUnifyStateBox->setChecked(m_part->deformUnified);
|
||||
|
@ -90,7 +90,7 @@ ComponentPropertyWidget::ComponentPropertyWidget(Document *document,
|
|||
emit groupOperationAdded();
|
||||
});
|
||||
|
||||
QHBoxLayout *deformUnifyLayout = new QHBoxLayout;
|
||||
QHBoxLayout* deformUnifyLayout = new QHBoxLayout;
|
||||
deformUnifyLayout->addStretch();
|
||||
deformUnifyLayout->addWidget(deformUnifyStateBox);
|
||||
|
||||
|
@ -102,9 +102,9 @@ ComponentPropertyWidget::ComponentPropertyWidget(Document *document,
|
|||
deformGroupBox->setLayout(deformLayout);
|
||||
}
|
||||
|
||||
QGroupBox *cutFaceGroupBox = nullptr;
|
||||
QGroupBox* cutFaceGroupBox = nullptr;
|
||||
if (nullptr != m_part) {
|
||||
FloatNumberWidget *rotationWidget = new FloatNumberWidget;
|
||||
FloatNumberWidget* rotationWidget = new FloatNumberWidget;
|
||||
rotationWidget->setItemName(tr("Rotation"));
|
||||
rotationWidget->setRange(-1, 1);
|
||||
rotationWidget->setValue(m_part->cutRotation);
|
||||
|
@ -114,7 +114,7 @@ ComponentPropertyWidget::ComponentPropertyWidget(Document *document,
|
|||
emit groupOperationAdded();
|
||||
});
|
||||
|
||||
QPushButton *rotationEraser = new QPushButton(QChar(fa::eraser));
|
||||
QPushButton* rotationEraser = new QPushButton(QChar(fa::eraser));
|
||||
Theme::initIconButton(rotationEraser);
|
||||
|
||||
connect(rotationEraser, &QPushButton::clicked, [=]() {
|
||||
|
@ -122,7 +122,7 @@ ComponentPropertyWidget::ComponentPropertyWidget(Document *document,
|
|||
emit groupOperationAdded();
|
||||
});
|
||||
|
||||
QPushButton *rotationMinus5Button = new QPushButton(QChar(fa::rotateleft));
|
||||
QPushButton* rotationMinus5Button = new QPushButton(QChar(fa::rotateleft));
|
||||
Theme::initIconButton(rotationMinus5Button);
|
||||
|
||||
connect(rotationMinus5Button, &QPushButton::clicked, [=]() {
|
||||
|
@ -130,7 +130,7 @@ ComponentPropertyWidget::ComponentPropertyWidget(Document *document,
|
|||
emit groupOperationAdded();
|
||||
});
|
||||
|
||||
QPushButton *rotation5Button = new QPushButton(QChar(fa::rotateright));
|
||||
QPushButton* rotation5Button = new QPushButton(QChar(fa::rotateright));
|
||||
Theme::initIconButton(rotation5Button);
|
||||
|
||||
connect(rotation5Button, &QPushButton::clicked, [=]() {
|
||||
|
@ -138,13 +138,13 @@ ComponentPropertyWidget::ComponentPropertyWidget(Document *document,
|
|||
emit groupOperationAdded();
|
||||
});
|
||||
|
||||
QHBoxLayout *rotationLayout = new QHBoxLayout;
|
||||
QHBoxLayout* rotationLayout = new QHBoxLayout;
|
||||
rotationLayout->addWidget(rotationEraser);
|
||||
rotationLayout->addWidget(rotationWidget);
|
||||
rotationLayout->addWidget(rotationMinus5Button);
|
||||
rotationLayout->addWidget(rotation5Button);
|
||||
|
||||
QCheckBox *subdivStateBox = new QCheckBox();
|
||||
QCheckBox* subdivStateBox = new QCheckBox();
|
||||
Theme::initCheckbox(subdivStateBox);
|
||||
subdivStateBox->setText(tr("Subdivided"));
|
||||
subdivStateBox->setChecked(m_part->subdived);
|
||||
|
@ -154,7 +154,7 @@ ComponentPropertyWidget::ComponentPropertyWidget(Document *document,
|
|||
emit groupOperationAdded();
|
||||
});
|
||||
|
||||
QCheckBox *chamferStateBox = new QCheckBox();
|
||||
QCheckBox* chamferStateBox = new QCheckBox();
|
||||
Theme::initCheckbox(chamferStateBox);
|
||||
chamferStateBox->setText(tr("Chamfered"));
|
||||
chamferStateBox->setChecked(m_part->chamfered);
|
||||
|
@ -164,7 +164,7 @@ ComponentPropertyWidget::ComponentPropertyWidget(Document *document,
|
|||
emit groupOperationAdded();
|
||||
});
|
||||
|
||||
QCheckBox *roundEndStateBox = new QCheckBox();
|
||||
QCheckBox* roundEndStateBox = new QCheckBox();
|
||||
Theme::initCheckbox(roundEndStateBox);
|
||||
roundEndStateBox->setText(tr("Round end"));
|
||||
roundEndStateBox->setChecked(m_part->rounded);
|
||||
|
@ -174,13 +174,13 @@ ComponentPropertyWidget::ComponentPropertyWidget(Document *document,
|
|||
emit groupOperationAdded();
|
||||
});
|
||||
|
||||
QHBoxLayout *optionsLayout = new QHBoxLayout;
|
||||
QHBoxLayout* optionsLayout = new QHBoxLayout;
|
||||
optionsLayout->addStretch();
|
||||
optionsLayout->addWidget(roundEndStateBox);
|
||||
optionsLayout->addWidget(chamferStateBox);
|
||||
optionsLayout->addWidget(subdivStateBox);
|
||||
|
||||
QVBoxLayout *cutFaceLayout = new QVBoxLayout;
|
||||
QVBoxLayout* cutFaceLayout = new QVBoxLayout;
|
||||
cutFaceLayout->addLayout(rotationLayout);
|
||||
cutFaceLayout->addLayout(optionsLayout);
|
||||
|
||||
|
@ -188,7 +188,7 @@ ComponentPropertyWidget::ComponentPropertyWidget(Document *document,
|
|||
cutFaceGroupBox->setLayout(cutFaceLayout);
|
||||
}
|
||||
|
||||
QVBoxLayout *mainLayout = new QVBoxLayout;
|
||||
QVBoxLayout* mainLayout = new QVBoxLayout;
|
||||
mainLayout->addLayout(colorLayout);
|
||||
if (nullptr != deformGroupBox)
|
||||
mainLayout->addWidget(deformGroupBox);
|
||||
|
@ -216,10 +216,10 @@ ComponentPropertyWidget::ComponentPropertyWidget(Document *document,
|
|||
void ComponentPropertyWidget::preparePartIds()
|
||||
{
|
||||
std::unordered_set<dust3d::Uuid> addedPartIdSet;
|
||||
for (const auto &componentId: m_componentIds) {
|
||||
for (const auto& componentId : m_componentIds) {
|
||||
std::vector<dust3d::Uuid> partIds;
|
||||
m_document->collectComponentDescendantParts(componentId, partIds);
|
||||
for (const auto &it: partIds) {
|
||||
for (const auto& it : partIds) {
|
||||
if (addedPartIdSet.insert(it).second)
|
||||
m_partIds.emplace_back(it);
|
||||
}
|
||||
|
@ -235,17 +235,17 @@ QColor ComponentPropertyWidget::lastColor()
|
|||
{
|
||||
QColor color = Qt::white;
|
||||
std::map<QString, int> colorMap;
|
||||
for (const auto &partId: m_partIds) {
|
||||
const SkeletonPart *part = m_document->findPart(partId);
|
||||
for (const auto& partId : m_partIds) {
|
||||
const SkeletonPart* part = m_document->findPart(partId);
|
||||
if (nullptr == part)
|
||||
continue;
|
||||
colorMap[part->color.name()]++;
|
||||
}
|
||||
if (!colorMap.empty()) {
|
||||
color = std::max_element(colorMap.begin(), colorMap.end(),
|
||||
[](const std::map<QString, int>::value_type &a, const std::map<QString, int>::value_type &b) {
|
||||
return a.second < b.second;
|
||||
})->first;
|
||||
[](const std::map<QString, int>::value_type& a, const std::map<QString, int>::value_type& b) {
|
||||
return a.second < b.second;
|
||||
})->first;
|
||||
}
|
||||
return color;
|
||||
}
|
||||
|
@ -258,7 +258,7 @@ void ComponentPropertyWidget::showColorDialog()
|
|||
if (!color.isValid())
|
||||
return;
|
||||
|
||||
for (const auto &partId: m_partIds) {
|
||||
for (const auto& partId : m_partIds) {
|
||||
emit setPartColorState(partId, true, color);
|
||||
}
|
||||
emit groupOperationAdded();
|
||||
|
|
|
@ -1,39 +1,40 @@
|
|||
#ifndef DUST3D_APPLICATION_COMPONENT_PROPERTY_WIDGET_H_
|
||||
#define DUST3D_APPLICATION_COMPONENT_PROPERTY_WIDGET_H_
|
||||
|
||||
#include <dust3d/base/uuid.h>
|
||||
#include <QWidget>
|
||||
#include <dust3d/base/uuid.h>
|
||||
|
||||
class Document;
|
||||
class SkeletonPart;
|
||||
|
||||
class ComponentPropertyWidget: public QWidget
|
||||
{
|
||||
class ComponentPropertyWidget : public QWidget {
|
||||
Q_OBJECT
|
||||
signals:
|
||||
void beginColorPicking();
|
||||
void endColorPicking();
|
||||
void setPartColorState(const dust3d::Uuid &partId, bool hasColor, const QColor &color);
|
||||
void setPartDeformThickness(const dust3d::Uuid &partId, float thickness);
|
||||
void setPartDeformWidth(const dust3d::Uuid &partId, float width);
|
||||
void setPartDeformUnified(const dust3d::Uuid &partId, bool unified);
|
||||
void setPartSubdivState(const dust3d::Uuid &partId, bool subdived);
|
||||
void setPartChamferState(const dust3d::Uuid &partId, bool chamfered);
|
||||
void setPartRoundState(const dust3d::Uuid &partId, bool rounded);
|
||||
void setPartCutRotation(const dust3d::Uuid &partId, float cutRotation);
|
||||
void setPartColorState(const dust3d::Uuid& partId, bool hasColor, const QColor& color);
|
||||
void setPartDeformThickness(const dust3d::Uuid& partId, float thickness);
|
||||
void setPartDeformWidth(const dust3d::Uuid& partId, float width);
|
||||
void setPartDeformUnified(const dust3d::Uuid& partId, bool unified);
|
||||
void setPartSubdivState(const dust3d::Uuid& partId, bool subdived);
|
||||
void setPartChamferState(const dust3d::Uuid& partId, bool chamfered);
|
||||
void setPartRoundState(const dust3d::Uuid& partId, bool rounded);
|
||||
void setPartCutRotation(const dust3d::Uuid& partId, float cutRotation);
|
||||
void groupOperationAdded();
|
||||
|
||||
public:
|
||||
ComponentPropertyWidget(Document *document,
|
||||
const std::vector<dust3d::Uuid> &componentIds,
|
||||
QWidget *parent=nullptr);
|
||||
ComponentPropertyWidget(Document* document,
|
||||
const std::vector<dust3d::Uuid>& componentIds,
|
||||
QWidget* parent = nullptr);
|
||||
public slots:
|
||||
void showColorDialog();
|
||||
|
||||
private:
|
||||
Document *m_document = nullptr;
|
||||
Document* m_document = nullptr;
|
||||
std::vector<dust3d::Uuid> m_componentIds;
|
||||
std::vector<dust3d::Uuid> m_partIds;
|
||||
dust3d::Uuid m_partId;
|
||||
const SkeletonPart *m_part = nullptr;
|
||||
const SkeletonPart* m_part = nullptr;
|
||||
QColor m_color;
|
||||
QColor lastColor();
|
||||
void preparePartIds();
|
||||
|
|
|
@ -1,13 +1,13 @@
|
|||
#include <QPainter>
|
||||
#include <QPainterPath>
|
||||
#include "cut_face_preview.h"
|
||||
#include "theme.h"
|
||||
#include <QPainter>
|
||||
#include <QPainterPath>
|
||||
|
||||
static std::map<int, QImage *> g_standardCutFaceMap;
|
||||
static std::map<int, QImage*> g_standardCutFaceMap;
|
||||
|
||||
QImage *buildCutFaceTemplatePreviewImage(const std::vector<dust3d::Vector2> &cutTemplate)
|
||||
QImage* buildCutFaceTemplatePreviewImage(const std::vector<dust3d::Vector2>& cutTemplate)
|
||||
{
|
||||
QImage *image = new QImage(Theme::partPreviewImageSize, Theme::partPreviewImageSize, QImage::Format_ARGB32);
|
||||
QImage* image = new QImage(Theme::partPreviewImageSize, Theme::partPreviewImageSize, QImage::Format_ARGB32);
|
||||
image->fill(Qt::transparent);
|
||||
|
||||
if (cutTemplate.empty())
|
||||
|
@ -30,7 +30,7 @@ QImage *buildCutFaceTemplatePreviewImage(const std::vector<dust3d::Vector2> &cut
|
|||
const float scale = 0.7f;
|
||||
QPolygon polygon;
|
||||
for (size_t i = 0; i <= cutTemplate.size(); ++i) {
|
||||
const auto &it = cutTemplate[i % cutTemplate.size()];
|
||||
const auto& it = cutTemplate[i % cutTemplate.size()];
|
||||
polygon.append(QPoint((it.x() * scale + 1.0) * 0.5 * Theme::partPreviewImageSize,
|
||||
(it.y() * scale + 1.0) * 0.5 * Theme::partPreviewImageSize));
|
||||
}
|
||||
|
@ -45,13 +45,13 @@ QImage *buildCutFaceTemplatePreviewImage(const std::vector<dust3d::Vector2> &cut
|
|||
return image;
|
||||
}
|
||||
|
||||
const QImage *cutFacePreviewImage(dust3d::CutFace cutFace)
|
||||
const QImage* cutFacePreviewImage(dust3d::CutFace cutFace)
|
||||
{
|
||||
auto findItem = g_standardCutFaceMap.find((int)cutFace);
|
||||
if (findItem != g_standardCutFaceMap.end())
|
||||
return findItem->second;
|
||||
std::vector<dust3d::Vector2> cutTemplate = dust3d::CutFaceToPoints(cutFace);
|
||||
QImage *image = buildCutFaceTemplatePreviewImage(cutTemplate);
|
||||
g_standardCutFaceMap.insert({(int)cutFace, image});
|
||||
QImage* image = buildCutFaceTemplatePreviewImage(cutTemplate);
|
||||
g_standardCutFaceMap.insert({ (int)cutFace, image });
|
||||
return image;
|
||||
}
|
||||
|
|
|
@ -4,7 +4,7 @@
|
|||
#include <QImage>
|
||||
#include <dust3d/base/cut_face.h>
|
||||
|
||||
QImage *buildCutFaceTemplatePreviewImage(const std::vector<dust3d::Vector2> &cutTemplate);
|
||||
const QImage *cutFacePreviewImage(dust3d::CutFace cutFace);
|
||||
QImage* buildCutFaceTemplatePreviewImage(const std::vector<dust3d::Vector2>& cutTemplate);
|
||||
const QImage* cutFacePreviewImage(dust3d::CutFace cutFace);
|
||||
|
||||
#endif
|
||||
|
|
|
@ -1,10 +1,10 @@
|
|||
#include <QtGlobal>
|
||||
#include <QFile>
|
||||
#include <QDebug>
|
||||
#include <QtEndian>
|
||||
#include <QByteArray>
|
||||
#include <QOpenGLPixelTransferOptions>
|
||||
#include "dds_file.h"
|
||||
#include <QByteArray>
|
||||
#include <QDebug>
|
||||
#include <QFile>
|
||||
#include <QOpenGLPixelTransferOptions>
|
||||
#include <QtEndian>
|
||||
#include <QtGlobal>
|
||||
|
||||
#ifndef _WIN32
|
||||
typedef quint32 DWORD;
|
||||
|
@ -37,20 +37,20 @@ typedef enum {
|
|||
} DDS_CAPS2_FLAGS;
|
||||
|
||||
typedef struct {
|
||||
DWORD dwSize;
|
||||
DWORD dwFlags;
|
||||
DWORD dwHeight;
|
||||
DWORD dwWidth;
|
||||
DWORD dwPitchOrLinearSize;
|
||||
DWORD dwDepth;
|
||||
DWORD dwMipMapCount;
|
||||
DWORD dwReserved1[11];
|
||||
DWORD dwSize;
|
||||
DWORD dwFlags;
|
||||
DWORD dwHeight;
|
||||
DWORD dwWidth;
|
||||
DWORD dwPitchOrLinearSize;
|
||||
DWORD dwDepth;
|
||||
DWORD dwMipMapCount;
|
||||
DWORD dwReserved1[11];
|
||||
DDS_PIXELFORMAT ddspf;
|
||||
DWORD dwCaps;
|
||||
DWORD dwCaps2;
|
||||
DWORD dwCaps3;
|
||||
DWORD dwCaps4;
|
||||
DWORD dwReserved2;
|
||||
DWORD dwCaps;
|
||||
DWORD dwCaps2;
|
||||
DWORD dwCaps3;
|
||||
DWORD dwCaps4;
|
||||
DWORD dwReserved2;
|
||||
} DDS_HEADER;
|
||||
|
||||
typedef enum {
|
||||
|
@ -176,9 +176,9 @@ typedef enum {
|
|||
DXGI_FORMAT_FORCE_UINT
|
||||
} DXGI_FORMAT;
|
||||
|
||||
static const char *DxgiFormatToString(DXGI_FORMAT dxgiFormat)
|
||||
static const char* DxgiFormatToString(DXGI_FORMAT dxgiFormat)
|
||||
{
|
||||
static const char *names[] = {
|
||||
static const char* names[] = {
|
||||
"DXGI_FORMAT_UNKNOWN",
|
||||
"DXGI_FORMAT_R32G32B32A32_TYPELESS",
|
||||
"DXGI_FORMAT_R32G32B32A32_FLOAT",
|
||||
|
@ -314,9 +314,9 @@ typedef enum {
|
|||
D3D10_RESOURCE_DIMENSION_TEXTURE3D
|
||||
} D3D10_RESOURCE_DIMENSION;
|
||||
|
||||
static const char *ResourceDimensionToString(D3D10_RESOURCE_DIMENSION resourceDimension)
|
||||
static const char* ResourceDimensionToString(D3D10_RESOURCE_DIMENSION resourceDimension)
|
||||
{
|
||||
static const char *names[] = {
|
||||
static const char* names[] = {
|
||||
"D3D10_RESOURCE_DIMENSION_UNKNOWN",
|
||||
"D3D10_RESOURCE_DIMENSION_BUFFER",
|
||||
"D3D10_RESOURCE_DIMENSION_TEXTURE1D",
|
||||
|
@ -337,9 +337,9 @@ typedef enum {
|
|||
D3D10_RESOURCE_MISC_GDI_COMPATIBLE
|
||||
} D3D10_RESOURCE_MISC_FLAG;
|
||||
|
||||
static const char *MiscFlagToString(UINT miscFlag)
|
||||
static const char* MiscFlagToString(UINT miscFlag)
|
||||
{
|
||||
static const char *names[] = {
|
||||
static const char* names[] = {
|
||||
"D3D10_RESOURCE_MISC_GENERATE_MIPS",
|
||||
"D3D10_RESOURCE_MISC_SHARED",
|
||||
"D3D10_RESOURCE_MISC_TEXTURECUBE",
|
||||
|
@ -353,21 +353,21 @@ static const char *MiscFlagToString(UINT miscFlag)
|
|||
}
|
||||
|
||||
typedef struct {
|
||||
DXGI_FORMAT dxgiFormat;
|
||||
DXGI_FORMAT dxgiFormat;
|
||||
D3D10_RESOURCE_DIMENSION resourceDimension;
|
||||
UINT miscFlag;
|
||||
UINT arraySize;
|
||||
UINT miscFlags2;
|
||||
UINT miscFlag;
|
||||
UINT arraySize;
|
||||
UINT miscFlags2;
|
||||
} DDS_HEADER_DXT10;
|
||||
|
||||
typedef struct {
|
||||
DWORD dwMagic;
|
||||
DDS_HEADER header;
|
||||
DDS_HEADER_DXT10 header10;
|
||||
DWORD dwMagic;
|
||||
DDS_HEADER header;
|
||||
DDS_HEADER_DXT10 header10;
|
||||
} DDS_FILE_HEADER;
|
||||
|
||||
DdsFileReader::DdsFileReader(const QString &filename) :
|
||||
m_filename(filename)
|
||||
DdsFileReader::DdsFileReader(const QString& filename)
|
||||
: m_filename(filename)
|
||||
{
|
||||
}
|
||||
|
||||
|
@ -381,7 +381,7 @@ std::unique_ptr<std::vector<std::unique_ptr<QOpenGLTexture>>> DdsFileReader::cre
|
|||
}
|
||||
|
||||
DDS_FILE_HEADER fileHeader;
|
||||
if (sizeof(fileHeader) != file.read((char *)&fileHeader, sizeof(fileHeader))) {
|
||||
if (sizeof(fileHeader) != file.read((char*)&fileHeader, sizeof(fileHeader))) {
|
||||
qDebug() << "Read DDS file hader failed";
|
||||
return nullptr;
|
||||
}
|
||||
|
@ -488,7 +488,7 @@ std::unique_ptr<std::vector<std::unique_ptr<QOpenGLTexture>>> DdsFileReader::cre
|
|||
for (quint32 face = 0; face < faces; ++face) {
|
||||
for (quint32 level = 0; level < mipMapCount; ++level) {
|
||||
if (0 == layer && 0 == level) {
|
||||
QOpenGLTexture *texture = new QOpenGLTexture(QOpenGLTexture::Target2D);
|
||||
QOpenGLTexture* texture = new QOpenGLTexture(QOpenGLTexture::Target2D);
|
||||
texture->setMinificationFilter(QOpenGLTexture::NearestMipMapNearest);
|
||||
texture->setMagnificationFilter(QOpenGLTexture::Nearest);
|
||||
texture->setFormat(QOpenGLTexture::RGBA16F);
|
||||
|
@ -504,7 +504,7 @@ std::unique_ptr<std::vector<std::unique_ptr<QOpenGLTexture>>> DdsFileReader::cre
|
|||
return std::move(textures);
|
||||
}
|
||||
|
||||
QOpenGLTexture *DdsFileReader::createOpenGLTexture()
|
||||
QOpenGLTexture* DdsFileReader::createOpenGLTexture()
|
||||
{
|
||||
QFile file(m_filename);
|
||||
|
||||
|
@ -514,7 +514,7 @@ QOpenGLTexture *DdsFileReader::createOpenGLTexture()
|
|||
}
|
||||
|
||||
DDS_FILE_HEADER fileHeader;
|
||||
if (sizeof(fileHeader) != file.read((char *)&fileHeader, sizeof(fileHeader))) {
|
||||
if (sizeof(fileHeader) != file.read((char*)&fileHeader, sizeof(fileHeader))) {
|
||||
qDebug() << "Read DDS file hader failed";
|
||||
return nullptr;
|
||||
}
|
||||
|
|
|
@ -1,16 +1,16 @@
|
|||
#ifndef DUST3D_APPLICATION_DDS_FILE_H_
|
||||
#define DUST3D_APPLICATION_DDS_FILE_H_
|
||||
|
||||
#include <memory>
|
||||
#include <QString>
|
||||
#include <QOpenGLTexture>
|
||||
#include <QString>
|
||||
#include <memory>
|
||||
|
||||
class DdsFileReader
|
||||
{
|
||||
class DdsFileReader {
|
||||
public:
|
||||
DdsFileReader(const QString &filename);
|
||||
QOpenGLTexture *createOpenGLTexture();
|
||||
DdsFileReader(const QString& filename);
|
||||
QOpenGLTexture* createOpenGLTexture();
|
||||
std::unique_ptr<std::vector<std::unique_ptr<QOpenGLTexture>>> createOpenGLTextures();
|
||||
|
||||
private:
|
||||
QString m_filename;
|
||||
};
|
||||
|
|
|
@ -1,13 +1,13 @@
|
|||
#include "debug.h"
|
||||
|
||||
QDebug operator<<(QDebug debug, const dust3d::Uuid &uuid)
|
||||
QDebug operator<<(QDebug debug, const dust3d::Uuid& uuid)
|
||||
{
|
||||
QDebugStateSaver stateSaver(debug);
|
||||
debug.nospace() << uuid.toString().c_str();
|
||||
return debug;
|
||||
}
|
||||
|
||||
QDebug operator<<(QDebug debug, const std::string &string)
|
||||
QDebug operator<<(QDebug debug, const std::string& string)
|
||||
{
|
||||
QDebugStateSaver stateSaver(debug);
|
||||
debug.nospace() << string.c_str();
|
||||
|
|
|
@ -4,7 +4,7 @@
|
|||
#include <QDebug>
|
||||
#include <dust3d/base/uuid.h>
|
||||
|
||||
QDebug operator<<(QDebug debug, const dust3d::Uuid &uuid);
|
||||
QDebug operator<<(QDebug debug, const std::string &string);
|
||||
QDebug operator<<(QDebug debug, const dust3d::Uuid& uuid);
|
||||
QDebug operator<<(QDebug debug, const std::string& string);
|
||||
|
||||
#endif
|
||||
|
|
|
@ -1,34 +1,34 @@
|
|||
#include <QFileDialog>
|
||||
#include <QDebug>
|
||||
#include <QThread>
|
||||
#include <QGuiApplication>
|
||||
#include <QClipboard>
|
||||
#include <QMimeData>
|
||||
#include <QApplication>
|
||||
#include <QVector3D>
|
||||
#include <functional>
|
||||
#include <QtCore/qbuffer.h>
|
||||
#include <QElapsedTimer>
|
||||
#include <queue>
|
||||
#include <dust3d/base/snapshot_xml.h>
|
||||
#include <dust3d/base/texture_type.h>
|
||||
#include "document.h"
|
||||
#include "image_forever.h"
|
||||
#include "material_previews_generator.h"
|
||||
#include "mesh_generator.h"
|
||||
#include "mesh_result_post_processor.h"
|
||||
#include "texture_generator.h"
|
||||
#include "material_previews_generator.h"
|
||||
#include <QApplication>
|
||||
#include <QClipboard>
|
||||
#include <QDebug>
|
||||
#include <QElapsedTimer>
|
||||
#include <QFileDialog>
|
||||
#include <QGuiApplication>
|
||||
#include <QMimeData>
|
||||
#include <QThread>
|
||||
#include <QVector3D>
|
||||
#include <QtCore/qbuffer.h>
|
||||
#include <dust3d/base/snapshot_xml.h>
|
||||
#include <dust3d/base/texture_type.h>
|
||||
#include <functional>
|
||||
#include <queue>
|
||||
|
||||
unsigned long Document::m_maxSnapshot = 1000;
|
||||
|
||||
Document::Document() :
|
||||
SkeletonDocument()
|
||||
Document::Document()
|
||||
: SkeletonDocument()
|
||||
{
|
||||
}
|
||||
|
||||
Document::~Document()
|
||||
{
|
||||
delete (dust3d::MeshGenerator::GeneratedCacheContext *)m_generatedCacheContext;
|
||||
delete (dust3d::MeshGenerator::GeneratedCacheContext*)m_generatedCacheContext;
|
||||
delete m_resultMesh;
|
||||
delete m_postProcessedObject;
|
||||
delete textureImage;
|
||||
|
@ -55,7 +55,7 @@ bool Document::originSettled() const
|
|||
return !qFuzzyIsNull(getOriginX()) && !qFuzzyIsNull(getOriginY()) && !qFuzzyIsNull(getOriginZ());
|
||||
}
|
||||
|
||||
const Material *Document::findMaterial(dust3d::Uuid materialId) const
|
||||
const Material* Document::findMaterial(dust3d::Uuid materialId) const
|
||||
{
|
||||
auto it = materialMap.find(materialId);
|
||||
if (it == materialMap.end())
|
||||
|
@ -104,8 +104,7 @@ void Document::setNodeCutFaceLinkedId(dust3d::Uuid nodeId, dust3d::Uuid linkedId
|
|||
qDebug() << "Node not found:" << nodeId;
|
||||
return;
|
||||
}
|
||||
if (node->second.cutFace == dust3d::CutFace::UserDefined &&
|
||||
node->second.cutFaceLinkedId == linkedId)
|
||||
if (node->second.cutFace == dust3d::CutFace::UserDefined && node->second.cutFaceLinkedId == linkedId)
|
||||
return;
|
||||
node->second.setCutFaceLinkedId(linkedId);
|
||||
auto part = partMap.find(node->second.partId);
|
||||
|
@ -132,7 +131,7 @@ void Document::clearNodeCutFaceSettings(dust3d::Uuid nodeId)
|
|||
emit skeletonChanged();
|
||||
}
|
||||
|
||||
void Document::updateTurnaround(const QImage &image)
|
||||
void Document::updateTurnaround(const QImage& image)
|
||||
{
|
||||
turnaround = image;
|
||||
turnaroundPngByteArray.clear();
|
||||
|
@ -149,7 +148,7 @@ void Document::clearTurnaround()
|
|||
emit turnaroundChanged();
|
||||
}
|
||||
|
||||
void Document::updateTextureImage(QImage *image)
|
||||
void Document::updateTextureImage(QImage* image)
|
||||
{
|
||||
delete textureImageByteArray;
|
||||
textureImageByteArray = nullptr;
|
||||
|
@ -158,7 +157,7 @@ void Document::updateTextureImage(QImage *image)
|
|||
textureImage = image;
|
||||
}
|
||||
|
||||
void Document::updateTextureNormalImage(QImage *image)
|
||||
void Document::updateTextureNormalImage(QImage* image)
|
||||
{
|
||||
delete textureNormalImageByteArray;
|
||||
textureNormalImageByteArray = nullptr;
|
||||
|
@ -167,7 +166,7 @@ void Document::updateTextureNormalImage(QImage *image)
|
|||
textureNormalImage = image;
|
||||
}
|
||||
|
||||
void Document::updateTextureMetalnessImage(QImage *image)
|
||||
void Document::updateTextureMetalnessImage(QImage* image)
|
||||
{
|
||||
delete textureMetalnessImageByteArray;
|
||||
textureMetalnessImageByteArray = nullptr;
|
||||
|
@ -176,7 +175,7 @@ void Document::updateTextureMetalnessImage(QImage *image)
|
|||
textureMetalnessImage = image;
|
||||
}
|
||||
|
||||
void Document::updateTextureRoughnessImage(QImage *image)
|
||||
void Document::updateTextureRoughnessImage(QImage* image)
|
||||
{
|
||||
delete textureRoughnessImageByteArray;
|
||||
textureRoughnessImageByteArray = nullptr;
|
||||
|
@ -185,7 +184,7 @@ void Document::updateTextureRoughnessImage(QImage *image)
|
|||
textureRoughnessImage = image;
|
||||
}
|
||||
|
||||
void Document::updateTextureAmbientOcclusionImage(QImage *image)
|
||||
void Document::updateTextureAmbientOcclusionImage(QImage* image)
|
||||
{
|
||||
delete textureAmbientOcclusionImageByteArray;
|
||||
textureAmbientOcclusionImageByteArray = nullptr;
|
||||
|
@ -203,23 +202,22 @@ void Document::setEditMode(SkeletonDocumentEditMode mode)
|
|||
emit editModeChanged();
|
||||
}
|
||||
|
||||
void Document::toSnapshot(dust3d::Snapshot *snapshot, const std::set<dust3d::Uuid> &limitNodeIds,
|
||||
void Document::toSnapshot(dust3d::Snapshot* snapshot, const std::set<dust3d::Uuid>& limitNodeIds,
|
||||
DocumentToSnapshotFor forWhat,
|
||||
const std::set<dust3d::Uuid> &limitMaterialIds) const
|
||||
const std::set<dust3d::Uuid>& limitMaterialIds) const
|
||||
{
|
||||
if (DocumentToSnapshotFor::Document == forWhat ||
|
||||
DocumentToSnapshotFor::Nodes == forWhat) {
|
||||
if (DocumentToSnapshotFor::Document == forWhat || DocumentToSnapshotFor::Nodes == forWhat) {
|
||||
std::set<dust3d::Uuid> limitPartIds;
|
||||
std::set<dust3d::Uuid> limitComponentIds;
|
||||
for (const auto &nodeId: limitNodeIds) {
|
||||
const SkeletonNode *node = findNode(nodeId);
|
||||
for (const auto& nodeId : limitNodeIds) {
|
||||
const SkeletonNode* node = findNode(nodeId);
|
||||
if (!node)
|
||||
continue;
|
||||
const SkeletonPart *part = findPart(node->partId);
|
||||
const SkeletonPart* part = findPart(node->partId);
|
||||
if (!part)
|
||||
continue;
|
||||
limitPartIds.insert(node->partId);
|
||||
const SkeletonComponent *component = findComponent(part->componentId);
|
||||
const SkeletonComponent* component = findComponent(part->componentId);
|
||||
while (component) {
|
||||
limitComponentIds.insert(component->id);
|
||||
if (component->id.isNull())
|
||||
|
@ -227,7 +225,7 @@ void Document::toSnapshot(dust3d::Snapshot *snapshot, const std::set<dust3d::Uui
|
|||
component = findComponent(component->parentId);
|
||||
}
|
||||
}
|
||||
for (const auto &partIt : partMap) {
|
||||
for (const auto& partIt : partMap) {
|
||||
if (!limitPartIds.empty() && limitPartIds.find(partIt.first) == limitPartIds.end())
|
||||
continue;
|
||||
std::map<std::string, std::string> part;
|
||||
|
@ -281,7 +279,7 @@ void Document::toSnapshot(dust3d::Snapshot *snapshot, const std::set<dust3d::Uui
|
|||
part["smooth"] = "true";
|
||||
snapshot->parts[part["id"]] = part;
|
||||
}
|
||||
for (const auto &nodeIt: nodeMap) {
|
||||
for (const auto& nodeIt : nodeMap) {
|
||||
if (!limitNodeIds.empty() && limitNodeIds.find(nodeIt.first) == limitNodeIds.end())
|
||||
continue;
|
||||
std::map<std::string, std::string> node;
|
||||
|
@ -305,12 +303,10 @@ void Document::toSnapshot(dust3d::Snapshot *snapshot, const std::set<dust3d::Uui
|
|||
node["name"] = nodeIt.second.name.toUtf8().constData();
|
||||
snapshot->nodes[node["id"]] = node;
|
||||
}
|
||||
for (const auto &edgeIt: edgeMap) {
|
||||
for (const auto& edgeIt : edgeMap) {
|
||||
if (edgeIt.second.nodeIds.size() != 2)
|
||||
continue;
|
||||
if (!limitNodeIds.empty() &&
|
||||
(limitNodeIds.find(edgeIt.second.nodeIds[0]) == limitNodeIds.end() ||
|
||||
limitNodeIds.find(edgeIt.second.nodeIds[1]) == limitNodeIds.end()))
|
||||
if (!limitNodeIds.empty() && (limitNodeIds.find(edgeIt.second.nodeIds[0]) == limitNodeIds.end() || limitNodeIds.find(edgeIt.second.nodeIds[1]) == limitNodeIds.end()))
|
||||
continue;
|
||||
std::map<std::string, std::string> edge;
|
||||
edge["id"] = edgeIt.second.id.toString();
|
||||
|
@ -321,7 +317,7 @@ void Document::toSnapshot(dust3d::Snapshot *snapshot, const std::set<dust3d::Uui
|
|||
edge["name"] = edgeIt.second.name.toUtf8().constData();
|
||||
snapshot->edges[edge["id"]] = edge;
|
||||
}
|
||||
for (const auto &componentIt: componentMap) {
|
||||
for (const auto& componentIt : componentMap) {
|
||||
if (!limitComponentIds.empty() && limitComponentIds.find(componentIt.first) == limitComponentIds.end())
|
||||
continue;
|
||||
std::map<std::string, std::string> component;
|
||||
|
@ -332,7 +328,7 @@ void Document::toSnapshot(dust3d::Snapshot *snapshot, const std::set<dust3d::Uui
|
|||
component["combineMode"] = CombineModeToString(componentIt.second.combineMode);
|
||||
component["__dirty"] = componentIt.second.dirty ? "true" : "false";
|
||||
std::vector<std::string> childIdList;
|
||||
for (const auto &childId: componentIt.second.childrenIds) {
|
||||
for (const auto& childId : componentIt.second.childrenIds) {
|
||||
childIdList.push_back(childId.toString());
|
||||
}
|
||||
std::string children = dust3d::String::join(childIdList, ",");
|
||||
|
@ -349,7 +345,7 @@ void Document::toSnapshot(dust3d::Snapshot *snapshot, const std::set<dust3d::Uui
|
|||
}
|
||||
if (limitComponentIds.empty() || limitComponentIds.find(dust3d::Uuid()) != limitComponentIds.end()) {
|
||||
std::vector<std::string> childIdList;
|
||||
for (const auto &childId: rootComponent.childrenIds) {
|
||||
for (const auto& childId : rootComponent.childrenIds) {
|
||||
childIdList.push_back(childId.toString());
|
||||
}
|
||||
std::string children = dust3d::String::join(childIdList, ",");
|
||||
|
@ -357,9 +353,8 @@ void Document::toSnapshot(dust3d::Snapshot *snapshot, const std::set<dust3d::Uui
|
|||
snapshot->rootComponent["children"] = children;
|
||||
}
|
||||
}
|
||||
if (DocumentToSnapshotFor::Document == forWhat ||
|
||||
DocumentToSnapshotFor::Materials == forWhat) {
|
||||
for (const auto &materialId: materialIdList) {
|
||||
if (DocumentToSnapshotFor::Document == forWhat || DocumentToSnapshotFor::Materials == forWhat) {
|
||||
for (const auto& materialId : materialIdList) {
|
||||
if (!limitMaterialIds.empty() && limitMaterialIds.find(materialId) == limitMaterialIds.end())
|
||||
continue;
|
||||
auto findMaterialResult = materialMap.find(materialId);
|
||||
|
@ -367,16 +362,16 @@ void Document::toSnapshot(dust3d::Snapshot *snapshot, const std::set<dust3d::Uui
|
|||
qDebug() << "Find material failed:" << materialId;
|
||||
continue;
|
||||
}
|
||||
auto &materialIt = *findMaterialResult;
|
||||
auto& materialIt = *findMaterialResult;
|
||||
std::map<std::string, std::string> material;
|
||||
material["id"] = materialIt.second.id.toString();
|
||||
material["type"] = "MetalRoughness";
|
||||
if (!materialIt.second.name.isEmpty())
|
||||
material["name"] = materialIt.second.name.toUtf8().constData();
|
||||
std::vector<std::pair<std::map<std::string, std::string>, std::vector<std::map<std::string, std::string>>>> layers;
|
||||
for (const auto &layer: materialIt.second.layers) {
|
||||
for (const auto& layer : materialIt.second.layers) {
|
||||
std::vector<std::map<std::string, std::string>> maps;
|
||||
for (const auto &mapItem: layer.maps) {
|
||||
for (const auto& mapItem : layer.maps) {
|
||||
std::map<std::string, std::string> textureMap;
|
||||
textureMap["for"] = TextureTypeToString(mapItem.forWhat);
|
||||
textureMap["linkDataType"] = "imageId";
|
||||
|
@ -386,7 +381,7 @@ void Document::toSnapshot(dust3d::Snapshot *snapshot, const std::set<dust3d::Uui
|
|||
std::map<std::string, std::string> layerAttributes;
|
||||
if (!qFuzzyCompare((float)layer.tileScale, (float)1.0))
|
||||
layerAttributes["tileScale"] = std::to_string(layer.tileScale);
|
||||
layers.push_back({layerAttributes, maps});
|
||||
layers.push_back({ layerAttributes, maps });
|
||||
}
|
||||
snapshot->materials.push_back(std::make_pair(material, layers));
|
||||
}
|
||||
|
@ -400,17 +395,14 @@ void Document::toSnapshot(dust3d::Snapshot *snapshot, const std::set<dust3d::Uui
|
|||
}
|
||||
}
|
||||
|
||||
void Document::addFromSnapshot(const dust3d::Snapshot &snapshot, enum SnapshotSource source)
|
||||
void Document::addFromSnapshot(const dust3d::Snapshot& snapshot, enum SnapshotSource source)
|
||||
{
|
||||
bool isOriginChanged = false;
|
||||
if (SnapshotSource::Paste != source &&
|
||||
SnapshotSource::Import != source) {
|
||||
const auto &originXit = snapshot.canvas.find("originX");
|
||||
const auto &originYit = snapshot.canvas.find("originY");
|
||||
const auto &originZit = snapshot.canvas.find("originZ");
|
||||
if (originXit != snapshot.canvas.end() &&
|
||||
originYit != snapshot.canvas.end() &&
|
||||
originZit != snapshot.canvas.end()) {
|
||||
if (SnapshotSource::Paste != source && SnapshotSource::Import != source) {
|
||||
const auto& originXit = snapshot.canvas.find("originX");
|
||||
const auto& originYit = snapshot.canvas.find("originY");
|
||||
const auto& originZit = snapshot.canvas.find("originZ");
|
||||
if (originXit != snapshot.canvas.end() && originYit != snapshot.canvas.end() && originZit != snapshot.canvas.end()) {
|
||||
setOriginX(dust3d::String::toFloat(originXit->second));
|
||||
setOriginY(dust3d::String::toFloat(originYit->second));
|
||||
setOriginZ(dust3d::String::toFloat(originZit->second));
|
||||
|
@ -426,8 +418,8 @@ void Document::addFromSnapshot(const dust3d::Snapshot &snapshot, enum SnapshotSo
|
|||
std::set<dust3d::Uuid> inversePartIds;
|
||||
|
||||
std::map<dust3d::Uuid, dust3d::Uuid> oldNewIdMap;
|
||||
for (const auto &materialIt: snapshot.materials) {
|
||||
const auto &materialAttributes = materialIt.first;
|
||||
for (const auto& materialIt : snapshot.materials) {
|
||||
const auto& materialAttributes = materialIt.first;
|
||||
auto materialType = dust3d::String::valueOrEmpty(materialAttributes, "type");
|
||||
if ("MetalRoughness" != materialType) {
|
||||
qDebug() << "Unsupported material type:" << materialType;
|
||||
|
@ -437,15 +429,15 @@ void Document::addFromSnapshot(const dust3d::Snapshot &snapshot, enum SnapshotSo
|
|||
dust3d::Uuid newMaterialId = SnapshotSource::Import == source ? oldMaterialId : dust3d::Uuid::createUuid();
|
||||
oldNewIdMap[oldMaterialId] = newMaterialId;
|
||||
if (materialMap.end() == materialMap.find(newMaterialId)) {
|
||||
auto &newMaterial = materialMap[newMaterialId];
|
||||
auto& newMaterial = materialMap[newMaterialId];
|
||||
newMaterial.id = newMaterialId;
|
||||
newMaterial.name = dust3d::String::valueOrEmpty(materialAttributes, "name").c_str();
|
||||
for (const auto &layerIt: materialIt.second) {
|
||||
for (const auto& layerIt : materialIt.second) {
|
||||
MaterialLayer layer;
|
||||
auto findTileScale = layerIt.first.find("tileScale");
|
||||
if (findTileScale != layerIt.first.end())
|
||||
layer.tileScale = dust3d::String::toFloat(findTileScale->second);
|
||||
for (const auto &mapItem: layerIt.second) {
|
||||
for (const auto& mapItem : layerIt.second) {
|
||||
auto textureTypeString = dust3d::String::valueOrEmpty(mapItem, "for");
|
||||
auto textureType = dust3d::TextureTypeFromString(textureTypeString.c_str());
|
||||
if (dust3d::TextureType::None == textureType) {
|
||||
|
@ -470,13 +462,13 @@ void Document::addFromSnapshot(const dust3d::Snapshot &snapshot, enum SnapshotSo
|
|||
}
|
||||
}
|
||||
std::map<dust3d::Uuid, dust3d::Uuid> cutFaceLinkedIdModifyMap;
|
||||
for (const auto &partKv: snapshot.parts) {
|
||||
for (const auto& partKv : snapshot.parts) {
|
||||
const auto newUuid = dust3d::Uuid::createUuid();
|
||||
SkeletonPart &part = partMap[newUuid];
|
||||
SkeletonPart& part = partMap[newUuid];
|
||||
part.id = newUuid;
|
||||
oldNewIdMap[dust3d::Uuid(partKv.first)] = part.id;
|
||||
part.name = dust3d::String::valueOrEmpty(partKv.second, "name").c_str();
|
||||
const auto &visibleIt = partKv.second.find("visible");
|
||||
const auto& visibleIt = partKv.second.find("visible");
|
||||
if (visibleIt != partKv.second.end()) {
|
||||
part.visible = dust3d::String::isTrue(visibleIt->second);
|
||||
} else {
|
||||
|
@ -490,56 +482,56 @@ void Document::addFromSnapshot(const dust3d::Snapshot &snapshot, enum SnapshotSo
|
|||
part.rounded = dust3d::String::isTrue(dust3d::String::valueOrEmpty(partKv.second, "rounded"));
|
||||
part.chamfered = dust3d::String::isTrue(dust3d::String::valueOrEmpty(partKv.second, "chamfered"));
|
||||
part.target = dust3d::PartTargetFromString(dust3d::String::valueOrEmpty(partKv.second, "target").c_str());
|
||||
const auto &cutRotationIt = partKv.second.find("cutRotation");
|
||||
const auto& cutRotationIt = partKv.second.find("cutRotation");
|
||||
if (cutRotationIt != partKv.second.end())
|
||||
part.setCutRotation(dust3d::String::toFloat(cutRotationIt->second));
|
||||
const auto &cutFaceIt = partKv.second.find("cutFace");
|
||||
const auto& cutFaceIt = partKv.second.find("cutFace");
|
||||
if (cutFaceIt != partKv.second.end()) {
|
||||
dust3d::Uuid cutFaceLinkedId = dust3d::Uuid(cutFaceIt->second);
|
||||
if (cutFaceLinkedId.isNull()) {
|
||||
part.setCutFace(dust3d::CutFaceFromString(cutFaceIt->second.c_str()));
|
||||
} else {
|
||||
part.setCutFaceLinkedId(cutFaceLinkedId);
|
||||
cutFaceLinkedIdModifyMap.insert({part.id, cutFaceLinkedId});
|
||||
cutFaceLinkedIdModifyMap.insert({ part.id, cutFaceLinkedId });
|
||||
}
|
||||
}
|
||||
if (dust3d::String::isTrue(dust3d::String::valueOrEmpty(partKv.second, "inverse")))
|
||||
inversePartIds.insert(part.id);
|
||||
const auto &colorIt = partKv.second.find("color");
|
||||
const auto& colorIt = partKv.second.find("color");
|
||||
if (colorIt != partKv.second.end()) {
|
||||
part.color = QColor(colorIt->second.c_str());
|
||||
part.hasColor = true;
|
||||
}
|
||||
const auto &colorSolubilityIt = partKv.second.find("colorSolubility");
|
||||
const auto& colorSolubilityIt = partKv.second.find("colorSolubility");
|
||||
if (colorSolubilityIt != partKv.second.end())
|
||||
part.colorSolubility = dust3d::String::toFloat(colorSolubilityIt->second);
|
||||
const auto &metalnessIt = partKv.second.find("metallic");
|
||||
const auto& metalnessIt = partKv.second.find("metallic");
|
||||
if (metalnessIt != partKv.second.end())
|
||||
part.metalness = dust3d::String::toFloat(metalnessIt->second);
|
||||
const auto &roughnessIt = partKv.second.find("roughness");
|
||||
const auto& roughnessIt = partKv.second.find("roughness");
|
||||
if (roughnessIt != partKv.second.end())
|
||||
part.roughness = dust3d::String::toFloat(roughnessIt->second);
|
||||
const auto &deformThicknessIt = partKv.second.find("deformThickness");
|
||||
const auto& deformThicknessIt = partKv.second.find("deformThickness");
|
||||
if (deformThicknessIt != partKv.second.end())
|
||||
part.setDeformThickness(dust3d::String::toFloat(deformThicknessIt->second));
|
||||
const auto &deformWidthIt = partKv.second.find("deformWidth");
|
||||
const auto& deformWidthIt = partKv.second.find("deformWidth");
|
||||
if (deformWidthIt != partKv.second.end())
|
||||
part.setDeformWidth(dust3d::String::toFloat(deformWidthIt->second));
|
||||
const auto &deformUnifiedIt = partKv.second.find("deformUnified");
|
||||
const auto& deformUnifiedIt = partKv.second.find("deformUnified");
|
||||
if (deformUnifiedIt != partKv.second.end())
|
||||
part.deformUnified = dust3d::String::isTrue(dust3d::String::valueOrEmpty(partKv.second, "deformUnified"));
|
||||
const auto &hollowThicknessIt = partKv.second.find("hollowThickness");
|
||||
const auto& hollowThicknessIt = partKv.second.find("hollowThickness");
|
||||
if (hollowThicknessIt != partKv.second.end())
|
||||
part.hollowThickness = dust3d::String::toFloat(hollowThicknessIt->second);
|
||||
const auto &materialIdIt = partKv.second.find("materialId");
|
||||
const auto& materialIdIt = partKv.second.find("materialId");
|
||||
if (materialIdIt != partKv.second.end())
|
||||
part.materialId = oldNewIdMap[dust3d::Uuid(materialIdIt->second)];
|
||||
part.countershaded = dust3d::String::isTrue(dust3d::String::valueOrEmpty(partKv.second, "countershaded"));
|
||||
part.smooth = dust3d::String::isTrue(dust3d::String::valueOrEmpty(partKv.second, "smooth"));
|
||||
newAddedPartIds.insert(part.id);
|
||||
}
|
||||
for (const auto &it: cutFaceLinkedIdModifyMap) {
|
||||
SkeletonPart &part = partMap[it.first];
|
||||
for (const auto& it : cutFaceLinkedIdModifyMap) {
|
||||
SkeletonPart& part = partMap[it.first];
|
||||
auto findNewLinkedId = oldNewIdMap.find(it.second);
|
||||
if (findNewLinkedId == oldNewIdMap.end()) {
|
||||
if (partMap.find(it.second) == partMap.end()) {
|
||||
|
@ -549,12 +541,8 @@ void Document::addFromSnapshot(const dust3d::Snapshot &snapshot, enum SnapshotSo
|
|||
part.setCutFaceLinkedId(findNewLinkedId->second);
|
||||
}
|
||||
}
|
||||
for (const auto &nodeKv: snapshot.nodes) {
|
||||
if (nodeKv.second.find("radius") == nodeKv.second.end() ||
|
||||
nodeKv.second.find("x") == nodeKv.second.end() ||
|
||||
nodeKv.second.find("y") == nodeKv.second.end() ||
|
||||
nodeKv.second.find("z") == nodeKv.second.end() ||
|
||||
nodeKv.second.find("partId") == nodeKv.second.end())
|
||||
for (const auto& nodeKv : snapshot.nodes) {
|
||||
if (nodeKv.second.find("radius") == nodeKv.second.end() || nodeKv.second.find("x") == nodeKv.second.end() || nodeKv.second.find("y") == nodeKv.second.end() || nodeKv.second.find("z") == nodeKv.second.end() || nodeKv.second.find("partId") == nodeKv.second.end())
|
||||
continue;
|
||||
dust3d::Uuid oldNodeId = dust3d::Uuid(nodeKv.first);
|
||||
SkeletonNode node(nodeMap.find(oldNodeId) == nodeMap.end() ? oldNodeId : dust3d::Uuid::createUuid());
|
||||
|
@ -565,10 +553,10 @@ void Document::addFromSnapshot(const dust3d::Snapshot &snapshot, enum SnapshotSo
|
|||
node.setY(dust3d::String::toFloat(dust3d::String::valueOrEmpty(nodeKv.second, "y")));
|
||||
node.setZ(dust3d::String::toFloat(dust3d::String::valueOrEmpty(nodeKv.second, "z")));
|
||||
node.partId = oldNewIdMap[dust3d::Uuid(dust3d::String::valueOrEmpty(nodeKv.second, "partId"))];
|
||||
const auto &cutRotationIt = nodeKv.second.find("cutRotation");
|
||||
const auto& cutRotationIt = nodeKv.second.find("cutRotation");
|
||||
if (cutRotationIt != nodeKv.second.end())
|
||||
node.setCutRotation(dust3d::String::toFloat(cutRotationIt->second));
|
||||
const auto &cutFaceIt = nodeKv.second.find("cutFace");
|
||||
const auto& cutFaceIt = nodeKv.second.find("cutFace");
|
||||
if (cutFaceIt != nodeKv.second.end()) {
|
||||
dust3d::Uuid cutFaceLinkedId = dust3d::Uuid(cutFaceIt->second);
|
||||
if (cutFaceLinkedId.isNull()) {
|
||||
|
@ -588,10 +576,8 @@ void Document::addFromSnapshot(const dust3d::Snapshot &snapshot, enum SnapshotSo
|
|||
nodeMap[node.id] = node;
|
||||
newAddedNodeIds.insert(node.id);
|
||||
}
|
||||
for (const auto &edgeKv: snapshot.edges) {
|
||||
if (edgeKv.second.find("from") == edgeKv.second.end() ||
|
||||
edgeKv.second.find("to") == edgeKv.second.end() ||
|
||||
edgeKv.second.find("partId") == edgeKv.second.end())
|
||||
for (const auto& edgeKv : snapshot.edges) {
|
||||
if (edgeKv.second.find("from") == edgeKv.second.end() || edgeKv.second.find("to") == edgeKv.second.end() || edgeKv.second.find("partId") == edgeKv.second.end())
|
||||
continue;
|
||||
dust3d::Uuid oldEdgeId = dust3d::Uuid(edgeKv.first);
|
||||
SkeletonEdge edge(edgeMap.find(oldEdgeId) == edgeMap.end() ? oldEdgeId : dust3d::Uuid::createUuid());
|
||||
|
@ -613,12 +599,12 @@ void Document::addFromSnapshot(const dust3d::Snapshot &snapshot, enum SnapshotSo
|
|||
edgeMap[edge.id] = edge;
|
||||
newAddedEdgeIds.insert(edge.id);
|
||||
}
|
||||
for (const auto &nodeIt: nodeMap) {
|
||||
for (const auto& nodeIt : nodeMap) {
|
||||
if (newAddedNodeIds.find(nodeIt.first) == newAddedNodeIds.end())
|
||||
continue;
|
||||
partMap[nodeIt.second.partId].nodeIds.push_back(nodeIt.first);
|
||||
}
|
||||
for (const auto &componentKv: snapshot.components) {
|
||||
for (const auto& componentKv : snapshot.components) {
|
||||
QString linkData = dust3d::String::valueOrEmpty(componentKv.second, "linkData").c_str();
|
||||
QString linkDataType = dust3d::String::valueOrEmpty(componentKv.second, "linkDataType").c_str();
|
||||
SkeletonComponent component(dust3d::Uuid(), linkData, linkDataType);
|
||||
|
@ -642,9 +628,9 @@ void Document::addFromSnapshot(const dust3d::Snapshot &snapshot, enum SnapshotSo
|
|||
componentMap.emplace(component.id, std::move(component));
|
||||
newAddedComponentIds.insert(component.id);
|
||||
}
|
||||
const auto &rootComponentChildren = snapshot.rootComponent.find("children");
|
||||
const auto& rootComponentChildren = snapshot.rootComponent.find("children");
|
||||
if (rootComponentChildren != snapshot.rootComponent.end()) {
|
||||
for (const auto &childId: dust3d::String::split(rootComponentChildren->second, ',')) {
|
||||
for (const auto& childId : dust3d::String::split(rootComponentChildren->second, ',')) {
|
||||
if (childId.empty())
|
||||
continue;
|
||||
dust3d::Uuid componentId = oldNewIdMap[dust3d::Uuid(childId)];
|
||||
|
@ -654,11 +640,11 @@ void Document::addFromSnapshot(const dust3d::Snapshot &snapshot, enum SnapshotSo
|
|||
rootComponent.addChild(componentId);
|
||||
}
|
||||
}
|
||||
for (const auto &componentKv: snapshot.components) {
|
||||
for (const auto& componentKv : snapshot.components) {
|
||||
dust3d::Uuid componentId = oldNewIdMap[dust3d::Uuid(componentKv.first)];
|
||||
if (componentMap.find(componentId) == componentMap.end())
|
||||
continue;
|
||||
for (const auto &childId: dust3d::String::split(dust3d::String::valueOrEmpty(componentKv.second, "children"), ',')) {
|
||||
for (const auto& childId : dust3d::String::split(dust3d::String::valueOrEmpty(componentKv.second, "children"), ',')) {
|
||||
if (childId.empty())
|
||||
continue;
|
||||
dust3d::Uuid childComponentId = oldNewIdMap[dust3d::Uuid(childId)];
|
||||
|
@ -670,13 +656,13 @@ void Document::addFromSnapshot(const dust3d::Snapshot &snapshot, enum SnapshotSo
|
|||
}
|
||||
}
|
||||
|
||||
for (const auto &nodeIt: newAddedNodeIds) {
|
||||
for (const auto& nodeIt : newAddedNodeIds) {
|
||||
emit nodeAdded(nodeIt);
|
||||
}
|
||||
for (const auto &edgeIt: newAddedEdgeIds) {
|
||||
for (const auto& edgeIt : newAddedEdgeIds) {
|
||||
emit edgeAdded(edgeIt);
|
||||
}
|
||||
for (const auto &partIt : newAddedPartIds) {
|
||||
for (const auto& partIt : newAddedPartIds) {
|
||||
emit partAdded(partIt);
|
||||
}
|
||||
|
||||
|
@ -685,15 +671,15 @@ void Document::addFromSnapshot(const dust3d::Snapshot &snapshot, enum SnapshotSo
|
|||
emit originChanged();
|
||||
emit skeletonChanged();
|
||||
|
||||
for (const auto &partIt : newAddedPartIds) {
|
||||
for (const auto& partIt : newAddedPartIds) {
|
||||
emit partVisibleStateChanged(partIt);
|
||||
}
|
||||
|
||||
emit uncheckAll();
|
||||
for (const auto &nodeIt: newAddedNodeIds) {
|
||||
for (const auto& nodeIt : newAddedNodeIds) {
|
||||
emit checkNode(nodeIt);
|
||||
}
|
||||
for (const auto &edgeIt: newAddedEdgeIds) {
|
||||
for (const auto& edgeIt : newAddedEdgeIds) {
|
||||
emit checkEdge(edgeIt);
|
||||
}
|
||||
|
||||
|
@ -722,22 +708,22 @@ void Document::reset()
|
|||
emit skeletonChanged();
|
||||
}
|
||||
|
||||
void Document::fromSnapshot(const dust3d::Snapshot &snapshot)
|
||||
void Document::fromSnapshot(const dust3d::Snapshot& snapshot)
|
||||
{
|
||||
reset();
|
||||
addFromSnapshot(snapshot, SnapshotSource::Unknown);
|
||||
emit uncheckAll();
|
||||
}
|
||||
|
||||
ModelMesh *Document::takeResultMesh()
|
||||
ModelMesh* Document::takeResultMesh()
|
||||
{
|
||||
if (nullptr == m_resultMesh)
|
||||
return nullptr;
|
||||
ModelMesh *resultMesh = new ModelMesh(*m_resultMesh);
|
||||
ModelMesh* resultMesh = new ModelMesh(*m_resultMesh);
|
||||
return resultMesh;
|
||||
}
|
||||
|
||||
MonochromeMesh *Document::takeWireframeMesh()
|
||||
MonochromeMesh* Document::takeWireframeMesh()
|
||||
{
|
||||
if (nullptr == m_wireframeMesh)
|
||||
return nullptr;
|
||||
|
@ -749,26 +735,26 @@ bool Document::isMeshGenerationSucceed()
|
|||
return m_isMeshGenerationSucceed;
|
||||
}
|
||||
|
||||
ModelMesh *Document::takeResultTextureMesh()
|
||||
ModelMesh* Document::takeResultTextureMesh()
|
||||
{
|
||||
if (nullptr == m_resultTextureMesh)
|
||||
return nullptr;
|
||||
ModelMesh *resultTextureMesh = new ModelMesh(*m_resultTextureMesh);
|
||||
ModelMesh* resultTextureMesh = new ModelMesh(*m_resultTextureMesh);
|
||||
return resultTextureMesh;
|
||||
}
|
||||
|
||||
void Document::meshReady()
|
||||
{
|
||||
ModelMesh *resultMesh = m_meshGenerator->takeResultMesh();
|
||||
ModelMesh* resultMesh = m_meshGenerator->takeResultMesh();
|
||||
m_wireframeMesh.reset(m_meshGenerator->takeWireframeMesh());
|
||||
dust3d::Object *object = m_meshGenerator->takeObject();
|
||||
dust3d::Object* object = m_meshGenerator->takeObject();
|
||||
bool isSuccessful = m_meshGenerator->isSuccessful();
|
||||
|
||||
std::unique_ptr<std::map<dust3d::Uuid, std::unique_ptr<ModelMesh>>> componentPreviewMeshes;
|
||||
componentPreviewMeshes.reset(m_meshGenerator->takeComponentPreviewMeshes());
|
||||
bool componentPreviewsChanged = componentPreviewMeshes && !componentPreviewMeshes->empty();
|
||||
if (componentPreviewsChanged) {
|
||||
for (auto &it: *componentPreviewMeshes) {
|
||||
for (auto& it : *componentPreviewMeshes) {
|
||||
setComponentPreviewMesh(it.first, std::move(it.second));
|
||||
}
|
||||
emit resultComponentPreviewMeshesChanged();
|
||||
|
@ -852,9 +838,9 @@ void Document::generateMesh()
|
|||
|
||||
m_isResultMeshObsolete = false;
|
||||
|
||||
QThread *thread = new QThread;
|
||||
QThread* thread = new QThread;
|
||||
|
||||
dust3d::Snapshot *snapshot = new dust3d::Snapshot;
|
||||
dust3d::Snapshot* snapshot = new dust3d::Snapshot;
|
||||
toSnapshot(snapshot);
|
||||
resetDirtyFlags();
|
||||
m_meshGenerator = new MeshGenerator(snapshot);
|
||||
|
@ -862,7 +848,7 @@ void Document::generateMesh()
|
|||
m_meshGenerator->setDefaultPartColor(dust3d::Color::createWhite());
|
||||
if (nullptr == m_generatedCacheContext)
|
||||
m_generatedCacheContext = new MeshGenerator::GeneratedCacheContext;
|
||||
m_meshGenerator->setGeneratedCacheContext((dust3d::MeshGenerator::GeneratedCacheContext *)m_generatedCacheContext);
|
||||
m_meshGenerator->setGeneratedCacheContext((dust3d::MeshGenerator::GeneratedCacheContext*)m_generatedCacheContext);
|
||||
if (!m_smoothNormal) {
|
||||
m_meshGenerator->setSmoothShadingThresholdAngleDegrees(0);
|
||||
}
|
||||
|
@ -886,10 +872,10 @@ void Document::generateTexture()
|
|||
|
||||
m_isTextureObsolete = false;
|
||||
|
||||
dust3d::Snapshot *snapshot = new dust3d::Snapshot;
|
||||
dust3d::Snapshot* snapshot = new dust3d::Snapshot;
|
||||
toSnapshot(snapshot);
|
||||
|
||||
QThread *thread = new QThread;
|
||||
QThread* thread = new QThread;
|
||||
m_textureGenerator = new TextureGenerator(*m_postProcessedObject, snapshot);
|
||||
m_textureGenerator->moveToThread(thread);
|
||||
connect(thread, &QThread::started, m_textureGenerator, &TextureGenerator::process);
|
||||
|
@ -945,7 +931,7 @@ void Document::postProcess()
|
|||
qDebug() << "Post processing..";
|
||||
emit postProcessing();
|
||||
|
||||
QThread *thread = new QThread;
|
||||
QThread* thread = new QThread;
|
||||
m_postProcessor = new MeshResultPostProcessor(*m_currentObject);
|
||||
m_postProcessor->moveToThread(thread);
|
||||
connect(thread, &QThread::started, m_postProcessor, &MeshResultPostProcessor::process);
|
||||
|
@ -972,7 +958,7 @@ void Document::postProcessedMeshResultReady()
|
|||
}
|
||||
}
|
||||
|
||||
const dust3d::Object &Document::currentPostProcessedObject() const
|
||||
const dust3d::Object& Document::currentPostProcessedObject() const
|
||||
{
|
||||
return *m_postProcessedObject;
|
||||
}
|
||||
|
@ -1007,7 +993,7 @@ void Document::setPartSubdivState(dust3d::Uuid partId, bool subdived)
|
|||
emit skeletonChanged();
|
||||
}
|
||||
|
||||
void Document::resolveSnapshotBoundingBox(const dust3d::Snapshot &snapshot, QRectF *mainProfile, QRectF *sideProfile)
|
||||
void Document::resolveSnapshotBoundingBox(const dust3d::Snapshot& snapshot, QRectF* mainProfile, QRectF* sideProfile)
|
||||
{
|
||||
float left = 0;
|
||||
bool leftFirstTime = true;
|
||||
|
@ -1021,7 +1007,7 @@ void Document::resolveSnapshotBoundingBox(const dust3d::Snapshot &snapshot, QRec
|
|||
bool zLeftFirstTime = true;
|
||||
float zRight = 0;
|
||||
bool zRightFirstTime = true;
|
||||
for (const auto &nodeIt: snapshot.nodes) {
|
||||
for (const auto& nodeIt : snapshot.nodes) {
|
||||
float radius = dust3d::String::toFloat(dust3d::String::valueOrEmpty(nodeIt.second, "radius"));
|
||||
float x = dust3d::String::toFloat(dust3d::String::valueOrEmpty(nodeIt.second, "x"));
|
||||
float y = dust3d::String::toFloat(dust3d::String::valueOrEmpty(nodeIt.second, "y"));
|
||||
|
@ -1330,8 +1316,7 @@ void Document::setPartCutFaceLinkedId(dust3d::Uuid partId, dust3d::Uuid linkedId
|
|||
qDebug() << "Part not found:" << partId;
|
||||
return;
|
||||
}
|
||||
if (part->second.cutFace == dust3d::CutFace::UserDefined &&
|
||||
part->second.cutFaceLinkedId == linkedId)
|
||||
if (part->second.cutFace == dust3d::CutFace::UserDefined && part->second.cutFaceLinkedId == linkedId)
|
||||
return;
|
||||
part->second.setCutFaceLinkedId(linkedId);
|
||||
part->second.dirty = true;
|
||||
|
@ -1370,7 +1355,7 @@ void Document::undo()
|
|||
return;
|
||||
m_redoItems.push_back(m_undoItems.back());
|
||||
m_undoItems.pop_back();
|
||||
const auto &item = m_undoItems.back();
|
||||
const auto& item = m_undoItems.back();
|
||||
fromSnapshot(item.snapshot);
|
||||
qDebug() << "Undo/Redo items:" << m_undoItems.size() << m_redoItems.size();
|
||||
}
|
||||
|
@ -1380,7 +1365,7 @@ void Document::redo()
|
|||
if (m_redoItems.empty())
|
||||
return;
|
||||
m_undoItems.push_back(m_redoItems.back());
|
||||
const auto &item = m_redoItems.back();
|
||||
const auto& item = m_redoItems.back();
|
||||
fromSnapshot(item.snapshot);
|
||||
m_redoItems.pop_back();
|
||||
qDebug() << "Undo/Redo items:" << m_undoItems.size() << m_redoItems.size();
|
||||
|
@ -1394,12 +1379,12 @@ void Document::clearHistories()
|
|||
|
||||
void Document::paste()
|
||||
{
|
||||
const QClipboard *clipboard = QApplication::clipboard();
|
||||
const QMimeData *mimeData = clipboard->mimeData();
|
||||
const QClipboard* clipboard = QApplication::clipboard();
|
||||
const QMimeData* mimeData = clipboard->mimeData();
|
||||
if (mimeData->hasText()) {
|
||||
dust3d::Snapshot snapshot;
|
||||
std::string text = mimeData->text().toUtf8().constData();
|
||||
loadSnapshotFromXmlString(&snapshot, (char *)text.c_str());
|
||||
loadSnapshotFromXmlString(&snapshot, (char*)text.c_str());
|
||||
addFromSnapshot(snapshot, SnapshotSource::Paste);
|
||||
saveSnapshot();
|
||||
}
|
||||
|
@ -1407,8 +1392,8 @@ void Document::paste()
|
|||
|
||||
bool Document::hasPastableNodesInClipboard() const
|
||||
{
|
||||
const QClipboard *clipboard = QApplication::clipboard();
|
||||
const QMimeData *mimeData = clipboard->mimeData();
|
||||
const QClipboard* clipboard = QApplication::clipboard();
|
||||
const QMimeData* mimeData = clipboard->mimeData();
|
||||
if (mimeData->hasText()) {
|
||||
if (-1 != mimeData->text().indexOf("<node "))
|
||||
return true;
|
||||
|
@ -1418,8 +1403,8 @@ bool Document::hasPastableNodesInClipboard() const
|
|||
|
||||
bool Document::hasPastableMaterialsInClipboard() const
|
||||
{
|
||||
const QClipboard *clipboard = QApplication::clipboard();
|
||||
const QMimeData *mimeData = clipboard->mimeData();
|
||||
const QClipboard* clipboard = QApplication::clipboard();
|
||||
const QMimeData* mimeData = clipboard->mimeData();
|
||||
if (mimeData->hasText()) {
|
||||
if (-1 != mimeData->text().indexOf("<material "))
|
||||
return true;
|
||||
|
@ -1439,7 +1424,7 @@ bool Document::redoable() const
|
|||
|
||||
bool Document::isNodeEditable(dust3d::Uuid nodeId) const
|
||||
{
|
||||
const SkeletonNode *node = findNode(nodeId);
|
||||
const SkeletonNode* node = findNode(nodeId);
|
||||
if (!node) {
|
||||
qDebug() << "Node id not found:" << nodeId;
|
||||
return false;
|
||||
|
@ -1449,7 +1434,7 @@ bool Document::isNodeEditable(dust3d::Uuid nodeId) const
|
|||
|
||||
bool Document::isEdgeEditable(dust3d::Uuid edgeId) const
|
||||
{
|
||||
const SkeletonEdge *edge = findEdge(edgeId);
|
||||
const SkeletonEdge* edge = findEdge(edgeId);
|
||||
if (!edge) {
|
||||
qDebug() << "Edge id not found:" << edgeId;
|
||||
return false;
|
||||
|
@ -1459,14 +1444,10 @@ bool Document::isEdgeEditable(dust3d::Uuid edgeId) const
|
|||
|
||||
bool Document::isExportReady() const
|
||||
{
|
||||
if (m_meshGenerator ||
|
||||
m_textureGenerator ||
|
||||
m_postProcessor)
|
||||
if (m_meshGenerator || m_textureGenerator || m_postProcessor)
|
||||
return false;
|
||||
|
||||
if (m_isResultMeshObsolete ||
|
||||
m_isTextureObsolete ||
|
||||
m_isPostProcessResultObsolete)
|
||||
if (m_isResultMeshObsolete || m_isTextureObsolete || m_isPostProcessResultObsolete)
|
||||
return false;
|
||||
|
||||
return true;
|
||||
|
@ -1487,7 +1468,7 @@ void Document::addMaterial(dust3d::Uuid materialId, QString name, std::vector<Ma
|
|||
}
|
||||
|
||||
dust3d::Uuid newMaterialId = materialId;
|
||||
auto &material = materialMap[newMaterialId];
|
||||
auto& material = materialMap[newMaterialId];
|
||||
material.id = newMaterialId;
|
||||
|
||||
material.name = name;
|
||||
|
@ -1552,10 +1533,10 @@ void Document::generateMaterialPreviews()
|
|||
return;
|
||||
}
|
||||
|
||||
QThread *thread = new QThread;
|
||||
QThread* thread = new QThread;
|
||||
m_materialPreviewsGenerator = new MaterialPreviewsGenerator();
|
||||
bool hasDirtyMaterial = false;
|
||||
for (auto &materialIt: materialMap) {
|
||||
for (auto& materialIt : materialMap) {
|
||||
if (!materialIt.second.dirty)
|
||||
continue;
|
||||
m_materialPreviewsGenerator->addMaterial(materialIt.first, materialIt.second.layers);
|
||||
|
@ -1581,10 +1562,10 @@ void Document::generateMaterialPreviews()
|
|||
|
||||
void Document::materialPreviewsReady()
|
||||
{
|
||||
for (const auto &materialId: m_materialPreviewsGenerator->generatedPreviewMaterialIds()) {
|
||||
for (const auto& materialId : m_materialPreviewsGenerator->generatedPreviewMaterialIds()) {
|
||||
auto material = materialMap.find(materialId);
|
||||
if (material != materialMap.end()) {
|
||||
ModelMesh *resultPartPreviewMesh = m_materialPreviewsGenerator->takePreview(materialId);
|
||||
ModelMesh* resultPartPreviewMesh = m_materialPreviewsGenerator->takePreview(materialId);
|
||||
material->second.updatePreviewMesh(resultPartPreviewMesh);
|
||||
emit materialPreviewChanged(materialId);
|
||||
}
|
||||
|
@ -1619,18 +1600,18 @@ void Document::copyNodes(std::set<dust3d::Uuid> nodeIdSet) const
|
|||
toSnapshot(&snapshot, nodeIdSet, DocumentToSnapshotFor::Nodes);
|
||||
std::string snapshotXml;
|
||||
dust3d::saveSnapshotToXmlString(snapshot, snapshotXml);
|
||||
QClipboard *clipboard = QApplication::clipboard();
|
||||
QClipboard* clipboard = QApplication::clipboard();
|
||||
clipboard->setText(snapshotXml.c_str());
|
||||
}
|
||||
|
||||
void Document::collectCutFaceList(std::vector<QString> &cutFaces) const
|
||||
void Document::collectCutFaceList(std::vector<QString>& cutFaces) const
|
||||
{
|
||||
cutFaces.clear();
|
||||
|
||||
std::vector<dust3d::Uuid> cutFacePartIdList;
|
||||
|
||||
std::set<dust3d::Uuid> cutFacePartIds;
|
||||
for (const auto &it: partMap) {
|
||||
for (const auto& it : partMap) {
|
||||
if (dust3d::PartTarget::CutFace == it.second.target) {
|
||||
if (cutFacePartIds.find(it.first) != cutFacePartIds.end())
|
||||
continue;
|
||||
|
@ -1647,13 +1628,13 @@ void Document::collectCutFaceList(std::vector<QString> &cutFaces) const
|
|||
|
||||
// Sort cut face by center.x of front view
|
||||
std::map<dust3d::Uuid, float> centerOffsetMap;
|
||||
for (const auto &partId: cutFacePartIdList) {
|
||||
const SkeletonPart *part = findPart(partId);
|
||||
for (const auto& partId : cutFacePartIdList) {
|
||||
const SkeletonPart* part = findPart(partId);
|
||||
if (nullptr == part)
|
||||
continue;
|
||||
float offsetSum = 0;
|
||||
for (const auto &nodeId: part->nodeIds) {
|
||||
const SkeletonNode *node = findNode(nodeId);
|
||||
for (const auto& nodeId : part->nodeIds) {
|
||||
const SkeletonNode* node = findNode(nodeId);
|
||||
if (nullptr == node)
|
||||
continue;
|
||||
offsetSum += node->getX();
|
||||
|
@ -1663,9 +1644,9 @@ void Document::collectCutFaceList(std::vector<QString> &cutFaces) const
|
|||
centerOffsetMap[partId] = offsetSum / part->nodeIds.size();
|
||||
}
|
||||
std::sort(cutFacePartIdList.begin(), cutFacePartIdList.end(),
|
||||
[&](const dust3d::Uuid &firstPartId, const dust3d::Uuid &secondPartId) {
|
||||
return centerOffsetMap[firstPartId] < centerOffsetMap[secondPartId];
|
||||
});
|
||||
[&](const dust3d::Uuid& firstPartId, const dust3d::Uuid& secondPartId) {
|
||||
return centerOffsetMap[firstPartId] < centerOffsetMap[secondPartId];
|
||||
});
|
||||
|
||||
size_t cutFaceTypeCount = (size_t)dust3d::CutFace::UserDefined;
|
||||
for (size_t i = 0; i < (size_t)cutFaceTypeCount; ++i) {
|
||||
|
@ -1673,6 +1654,6 @@ void Document::collectCutFaceList(std::vector<QString> &cutFaces) const
|
|||
cutFaces.push_back(QString(dust3d::CutFaceToString(cutFace).c_str()));
|
||||
}
|
||||
|
||||
for (const auto &it: cutFacePartIdList)
|
||||
for (const auto& it : cutFacePartIdList)
|
||||
cutFaces.push_back(QString(it.toString().c_str()));
|
||||
}
|
||||
|
|
|
@ -1,38 +1,36 @@
|
|||
#ifndef DUST3D_APPLICATION_DOCUMENT_H_
|
||||
#define DUST3D_APPLICATION_DOCUMENT_H_
|
||||
|
||||
#include <QObject>
|
||||
#include <vector>
|
||||
#include <map>
|
||||
#include <set>
|
||||
#include <deque>
|
||||
#include <QImage>
|
||||
#include <cmath>
|
||||
#include <algorithm>
|
||||
#include <QPolygon>
|
||||
#include <dust3d/base/uuid.h>
|
||||
#include <dust3d/base/snapshot.h>
|
||||
#include <dust3d/base/texture_type.h>
|
||||
#include <dust3d/base/combine_mode.h>
|
||||
#include "material_layer.h"
|
||||
#include "model_mesh.h"
|
||||
#include "monochrome_mesh.h"
|
||||
#include "theme.h"
|
||||
#include "skeleton_document.h"
|
||||
#include "material_layer.h"
|
||||
#include "theme.h"
|
||||
#include <QImage>
|
||||
#include <QObject>
|
||||
#include <QPolygon>
|
||||
#include <algorithm>
|
||||
#include <cmath>
|
||||
#include <deque>
|
||||
#include <dust3d/base/combine_mode.h>
|
||||
#include <dust3d/base/snapshot.h>
|
||||
#include <dust3d/base/texture_type.h>
|
||||
#include <dust3d/base/uuid.h>
|
||||
#include <map>
|
||||
#include <set>
|
||||
#include <vector>
|
||||
|
||||
class MaterialPreviewsGenerator;
|
||||
class TextureGenerator;
|
||||
class MeshGenerator;
|
||||
class MeshResultPostProcessor;
|
||||
|
||||
class HistoryItem
|
||||
{
|
||||
class HistoryItem {
|
||||
public:
|
||||
dust3d::Snapshot snapshot;
|
||||
};
|
||||
|
||||
class Material
|
||||
{
|
||||
class Material {
|
||||
public:
|
||||
Material()
|
||||
{
|
||||
|
@ -45,31 +43,30 @@ public:
|
|||
QString name;
|
||||
bool dirty = true;
|
||||
std::vector<MaterialLayer> layers;
|
||||
void updatePreviewMesh(ModelMesh *previewMesh)
|
||||
void updatePreviewMesh(ModelMesh* previewMesh)
|
||||
{
|
||||
delete m_previewMesh;
|
||||
m_previewMesh = previewMesh;
|
||||
}
|
||||
ModelMesh *takePreviewMesh() const
|
||||
ModelMesh* takePreviewMesh() const
|
||||
{
|
||||
if (nullptr == m_previewMesh)
|
||||
return nullptr;
|
||||
return new ModelMesh(*m_previewMesh);
|
||||
}
|
||||
|
||||
private:
|
||||
Q_DISABLE_COPY(Material);
|
||||
ModelMesh *m_previewMesh = nullptr;
|
||||
ModelMesh* m_previewMesh = nullptr;
|
||||
};
|
||||
|
||||
enum class DocumentToSnapshotFor
|
||||
{
|
||||
enum class DocumentToSnapshotFor {
|
||||
Document = 0,
|
||||
Nodes,
|
||||
Materials
|
||||
};
|
||||
|
||||
class Document : public SkeletonDocument
|
||||
{
|
||||
class Document : public SkeletonDocument {
|
||||
Q_OBJECT
|
||||
signals:
|
||||
void nodeCutRotationChanged(dust3d::Uuid nodeId);
|
||||
|
@ -121,20 +118,22 @@ signals:
|
|||
void postProcessing();
|
||||
void textureGenerating();
|
||||
void textureChanged();
|
||||
|
||||
public: // need initialize
|
||||
QImage *textureImage = nullptr;
|
||||
QByteArray *textureImageByteArray = nullptr;
|
||||
QImage *textureNormalImage = nullptr;
|
||||
QByteArray *textureNormalImageByteArray = nullptr;
|
||||
QImage *textureMetalnessImage = nullptr;
|
||||
QByteArray *textureMetalnessImageByteArray = nullptr;
|
||||
QImage *textureRoughnessImage = nullptr;
|
||||
QByteArray *textureRoughnessImageByteArray = nullptr;
|
||||
QImage *textureAmbientOcclusionImage = nullptr;
|
||||
QByteArray *textureAmbientOcclusionImageByteArray = nullptr;
|
||||
QImage* textureImage = nullptr;
|
||||
QByteArray* textureImageByteArray = nullptr;
|
||||
QImage* textureNormalImage = nullptr;
|
||||
QByteArray* textureNormalImageByteArray = nullptr;
|
||||
QImage* textureMetalnessImage = nullptr;
|
||||
QByteArray* textureMetalnessImageByteArray = nullptr;
|
||||
QImage* textureRoughnessImage = nullptr;
|
||||
QByteArray* textureRoughnessImageByteArray = nullptr;
|
||||
QImage* textureAmbientOcclusionImage = nullptr;
|
||||
QByteArray* textureAmbientOcclusionImageByteArray = nullptr;
|
||||
bool weldEnabled = true;
|
||||
float brushMetalness = ModelMesh::m_defaultMetalness;
|
||||
float brushRoughness = ModelMesh::m_defaultRoughness;
|
||||
|
||||
public:
|
||||
Document();
|
||||
~Document();
|
||||
|
@ -148,39 +147,38 @@ public:
|
|||
bool isNodeEditable(dust3d::Uuid nodeId) const override;
|
||||
bool isEdgeEditable(dust3d::Uuid edgeId) const override;
|
||||
void copyNodes(std::set<dust3d::Uuid> nodeIdSet) const override;
|
||||
void toSnapshot(dust3d::Snapshot *snapshot, const std::set<dust3d::Uuid> &limitNodeIds=std::set<dust3d::Uuid>(),
|
||||
DocumentToSnapshotFor forWhat=DocumentToSnapshotFor::Document,
|
||||
const std::set<dust3d::Uuid> &limitMaterialIds=std::set<dust3d::Uuid>()) const;
|
||||
void fromSnapshot(const dust3d::Snapshot &snapshot);
|
||||
enum class SnapshotSource
|
||||
{
|
||||
void toSnapshot(dust3d::Snapshot* snapshot, const std::set<dust3d::Uuid>& limitNodeIds = std::set<dust3d::Uuid>(),
|
||||
DocumentToSnapshotFor forWhat = DocumentToSnapshotFor::Document,
|
||||
const std::set<dust3d::Uuid>& limitMaterialIds = std::set<dust3d::Uuid>()) const;
|
||||
void fromSnapshot(const dust3d::Snapshot& snapshot);
|
||||
enum class SnapshotSource {
|
||||
Unknown,
|
||||
Paste,
|
||||
Import
|
||||
};
|
||||
void addFromSnapshot(const dust3d::Snapshot &snapshot, enum SnapshotSource source=SnapshotSource::Paste);
|
||||
const Material *findMaterial(dust3d::Uuid materialId) const;
|
||||
ModelMesh *takeResultMesh();
|
||||
MonochromeMesh *takeWireframeMesh();
|
||||
ModelMesh *takePaintedMesh();
|
||||
void addFromSnapshot(const dust3d::Snapshot& snapshot, enum SnapshotSource source = SnapshotSource::Paste);
|
||||
const Material* findMaterial(dust3d::Uuid materialId) const;
|
||||
ModelMesh* takeResultMesh();
|
||||
MonochromeMesh* takeWireframeMesh();
|
||||
ModelMesh* takePaintedMesh();
|
||||
bool isMeshGenerationSucceed();
|
||||
ModelMesh *takeResultTextureMesh();
|
||||
ModelMesh *takeResultRigWeightMesh();
|
||||
void updateTurnaround(const QImage &image);
|
||||
ModelMesh* takeResultTextureMesh();
|
||||
ModelMesh* takeResultRigWeightMesh();
|
||||
void updateTurnaround(const QImage& image);
|
||||
void clearTurnaround();
|
||||
void updateTextureImage(QImage *image);
|
||||
void updateTextureNormalImage(QImage *image);
|
||||
void updateTextureMetalnessImage(QImage *image);
|
||||
void updateTextureRoughnessImage(QImage *image);
|
||||
void updateTextureAmbientOcclusionImage(QImage *image);
|
||||
void updateTextureImage(QImage* image);
|
||||
void updateTextureNormalImage(QImage* image);
|
||||
void updateTextureMetalnessImage(QImage* image);
|
||||
void updateTextureRoughnessImage(QImage* image);
|
||||
void updateTextureAmbientOcclusionImage(QImage* image);
|
||||
bool hasPastableMaterialsInClipboard() const;
|
||||
const dust3d::Object ¤tPostProcessedObject() const;
|
||||
const dust3d::Object& currentPostProcessedObject() const;
|
||||
bool isExportReady() const;
|
||||
bool isPostProcessResultObsolete() const;
|
||||
bool isMeshGenerating() const;
|
||||
bool isPostProcessing() const;
|
||||
bool isTextureGenerating() const;
|
||||
void collectCutFaceList(std::vector<QString> &cutFaces) const;
|
||||
void collectCutFaceList(std::vector<QString>& cutFaces) const;
|
||||
public slots:
|
||||
void undo() override;
|
||||
void redo() override;
|
||||
|
@ -233,30 +231,32 @@ public slots:
|
|||
void removeMaterial(dust3d::Uuid materialId);
|
||||
void setMaterialLayers(dust3d::Uuid materialId, std::vector<MaterialLayer> layers);
|
||||
void renameMaterial(dust3d::Uuid materialId, QString name);
|
||||
|
||||
private:
|
||||
void resolveSnapshotBoundingBox(const dust3d::Snapshot &snapshot, QRectF *mainProfile, QRectF *sideProfile);
|
||||
void resolveSnapshotBoundingBox(const dust3d::Snapshot& snapshot, QRectF* mainProfile, QRectF* sideProfile);
|
||||
void settleOrigin();
|
||||
void checkExportReadyState();
|
||||
|
||||
bool m_isResultMeshObsolete = false;
|
||||
MeshGenerator *m_meshGenerator = nullptr;
|
||||
ModelMesh *m_resultMesh = nullptr;
|
||||
MeshGenerator* m_meshGenerator = nullptr;
|
||||
ModelMesh* m_resultMesh = nullptr;
|
||||
std::unique_ptr<MonochromeMesh> m_wireframeMesh;
|
||||
bool m_isMeshGenerationSucceed = true;
|
||||
int m_batchChangeRefCount = 0;
|
||||
dust3d::Object *m_currentObject = nullptr;
|
||||
dust3d::Object* m_currentObject = nullptr;
|
||||
bool m_isTextureObsolete = false;
|
||||
TextureGenerator *m_textureGenerator = nullptr;
|
||||
TextureGenerator* m_textureGenerator = nullptr;
|
||||
bool m_isPostProcessResultObsolete = false;
|
||||
MeshResultPostProcessor *m_postProcessor = nullptr;
|
||||
dust3d::Object *m_postProcessedObject = new dust3d::Object;
|
||||
ModelMesh *m_resultTextureMesh = nullptr;
|
||||
MeshResultPostProcessor* m_postProcessor = nullptr;
|
||||
dust3d::Object* m_postProcessedObject = new dust3d::Object;
|
||||
ModelMesh* m_resultTextureMesh = nullptr;
|
||||
unsigned long long m_textureImageUpdateVersion = 0;
|
||||
bool m_smoothNormal = false;
|
||||
MaterialPreviewsGenerator *m_materialPreviewsGenerator = nullptr;
|
||||
MaterialPreviewsGenerator* m_materialPreviewsGenerator = nullptr;
|
||||
quint64 m_meshGenerationId = 0;
|
||||
quint64 m_nextMeshGenerationId = 0;
|
||||
void *m_generatedCacheContext = nullptr;
|
||||
void* m_generatedCacheContext = nullptr;
|
||||
|
||||
private:
|
||||
static unsigned long m_maxSnapshot;
|
||||
std::deque<HistoryItem> m_undoItems;
|
||||
|
|
|
@ -1,17 +1,17 @@
|
|||
#include <set>
|
||||
#include "document_saver.h"
|
||||
#include "image_forever.h"
|
||||
#include <QGuiApplication>
|
||||
#include <QtCore/qbuffer.h>
|
||||
#include <dust3d/base/ds3_file.h>
|
||||
#include <dust3d/base/snapshot_xml.h>
|
||||
#include "document_saver.h"
|
||||
#include "image_forever.h"
|
||||
#include <set>
|
||||
|
||||
DocumentSaver::DocumentSaver(const QString *filename,
|
||||
dust3d::Snapshot *snapshot,
|
||||
QByteArray *turnaroundPngByteArray) :
|
||||
m_filename(filename),
|
||||
m_snapshot(snapshot),
|
||||
m_turnaroundPngByteArray(turnaroundPngByteArray)
|
||||
DocumentSaver::DocumentSaver(const QString* filename,
|
||||
dust3d::Snapshot* snapshot,
|
||||
QByteArray* turnaroundPngByteArray)
|
||||
: m_filename(filename)
|
||||
, m_snapshot(snapshot)
|
||||
, m_turnaroundPngByteArray(turnaroundPngByteArray)
|
||||
{
|
||||
}
|
||||
|
||||
|
@ -29,12 +29,12 @@ void DocumentSaver::process()
|
|||
emit finished();
|
||||
}
|
||||
|
||||
void DocumentSaver::collectUsedResourceIds(const dust3d::Snapshot *snapshot,
|
||||
std::set<dust3d::Uuid> &imageIds)
|
||||
void DocumentSaver::collectUsedResourceIds(const dust3d::Snapshot* snapshot,
|
||||
std::set<dust3d::Uuid>& imageIds)
|
||||
{
|
||||
for (const auto &material: snapshot->materials) {
|
||||
for (auto &layer: material.second) {
|
||||
for (auto &mapItem: layer.second) {
|
||||
for (const auto& material : snapshot->materials) {
|
||||
for (auto& layer : material.second) {
|
||||
for (auto& mapItem : layer.second) {
|
||||
auto findImageIdString = mapItem.find("linkData");
|
||||
if (findImageIdString == mapItem.end())
|
||||
continue;
|
||||
|
@ -45,9 +45,9 @@ void DocumentSaver::collectUsedResourceIds(const dust3d::Snapshot *snapshot,
|
|||
}
|
||||
}
|
||||
|
||||
bool DocumentSaver::save(const QString *filename,
|
||||
dust3d::Snapshot *snapshot,
|
||||
const QByteArray *turnaroundPngByteArray)
|
||||
bool DocumentSaver::save(const QString* filename,
|
||||
dust3d::Snapshot* snapshot,
|
||||
const QByteArray* turnaroundPngByteArray)
|
||||
{
|
||||
dust3d::Ds3FileWriter ds3Writer;
|
||||
|
||||
|
@ -65,8 +65,8 @@ bool DocumentSaver::save(const QString *filename,
|
|||
std::set<dust3d::Uuid> imageIds;
|
||||
collectUsedResourceIds(snapshot, imageIds);
|
||||
|
||||
for (const auto &imageId: imageIds) {
|
||||
const QByteArray *pngByteArray = ImageForever::getPngByteArray(imageId);
|
||||
for (const auto& imageId : imageIds) {
|
||||
const QByteArray* pngByteArray = ImageForever::getPngByteArray(imageId);
|
||||
if (nullptr == pngByteArray)
|
||||
continue;
|
||||
if (pngByteArray->size() > 0)
|
||||
|
|
|
@ -1,35 +1,35 @@
|
|||
#ifndef DUST3D_APPLICATION_DOCUMENT_SAVER_H_
|
||||
#define DUST3D_APPLICATION_DOCUMENT_SAVER_H_
|
||||
|
||||
#include <QString>
|
||||
#include <QObject>
|
||||
#include <QByteArray>
|
||||
#include <QObject>
|
||||
#include <QString>
|
||||
#include <dust3d/base/snapshot.h>
|
||||
#include <dust3d/base/uuid.h>
|
||||
#include <map>
|
||||
#include <set>
|
||||
#include <dust3d/base/uuid.h>
|
||||
#include <dust3d/base/snapshot.h>
|
||||
|
||||
class DocumentSaver : public QObject
|
||||
{
|
||||
class DocumentSaver : public QObject {
|
||||
Q_OBJECT
|
||||
public:
|
||||
DocumentSaver(const QString *filename,
|
||||
dust3d::Snapshot *snapshot,
|
||||
QByteArray *turnaroundPngByteArray);
|
||||
DocumentSaver(const QString* filename,
|
||||
dust3d::Snapshot* snapshot,
|
||||
QByteArray* turnaroundPngByteArray);
|
||||
~DocumentSaver();
|
||||
static bool save(const QString *filename,
|
||||
dust3d::Snapshot *snapshot,
|
||||
const QByteArray *turnaroundPngByteArray);
|
||||
static void collectUsedResourceIds(const dust3d::Snapshot *snapshot,
|
||||
std::set<dust3d::Uuid> &imageIds);
|
||||
static bool save(const QString* filename,
|
||||
dust3d::Snapshot* snapshot,
|
||||
const QByteArray* turnaroundPngByteArray);
|
||||
static void collectUsedResourceIds(const dust3d::Snapshot* snapshot,
|
||||
std::set<dust3d::Uuid>& imageIds);
|
||||
signals:
|
||||
void finished();
|
||||
public slots:
|
||||
void process();
|
||||
|
||||
private:
|
||||
const QString *m_filename = nullptr;
|
||||
dust3d::Snapshot *m_snapshot = nullptr;
|
||||
QByteArray *m_turnaroundPngByteArray = nullptr;
|
||||
const QString* m_filename = nullptr;
|
||||
dust3d::Snapshot* m_snapshot = nullptr;
|
||||
QByteArray* m_turnaroundPngByteArray = nullptr;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
@ -1,80 +1,81 @@
|
|||
#include <QVBoxLayout>
|
||||
#include <QHBoxLayout>
|
||||
#include <QLabel>
|
||||
#include <QGridLayout>
|
||||
#include <QToolBar>
|
||||
#include <QPushButton>
|
||||
#include <QFileDialog>
|
||||
#include <QTabWidget>
|
||||
#include <QtCore/qbuffer.h>
|
||||
#include <QMessageBox>
|
||||
#include <QTimer>
|
||||
#include <QMenuBar>
|
||||
#include <QPointer>
|
||||
#include "document_window.h"
|
||||
#include "about_widget.h"
|
||||
#include "cut_face_preview.h"
|
||||
#include "document.h"
|
||||
#include "document_saver.h"
|
||||
#include "fbx_file.h"
|
||||
#include "float_number_widget.h"
|
||||
#include "flow_layout.h"
|
||||
#include "glb_file.h"
|
||||
#include "horizontal_line_widget.h"
|
||||
#include "image_forever.h"
|
||||
#include "log_browser.h"
|
||||
#include "material_manage_widget.h"
|
||||
#include "part_manage_widget.h"
|
||||
#include "preferences.h"
|
||||
#include "skeleton_graphics_widget.h"
|
||||
#include "spinnable_toolbar_icon.h"
|
||||
#include "texture_generator.h"
|
||||
#include "theme.h"
|
||||
#include "updates_check_widget.h"
|
||||
#include "version.h"
|
||||
#include <QApplication>
|
||||
#include <map>
|
||||
#include <QDesktopServices>
|
||||
#include <QDockWidget>
|
||||
#include <QWidgetAction>
|
||||
#include <QGraphicsOpacityEffect>
|
||||
#include <QDir>
|
||||
#include <QDockWidget>
|
||||
#include <QFileDialog>
|
||||
#include <QFileInfo>
|
||||
#include <QFormLayout>
|
||||
#include <QTextBrowser>
|
||||
#include <QGraphicsOpacityEffect>
|
||||
#include <QGridLayout>
|
||||
#include <QHBoxLayout>
|
||||
#include <QLabel>
|
||||
#include <QMenuBar>
|
||||
#include <QMessageBox>
|
||||
#include <QMimeData>
|
||||
#include <QPixmap>
|
||||
#include <QPointer>
|
||||
#include <QPushButton>
|
||||
#include <QTabWidget>
|
||||
#include <QTextBrowser>
|
||||
#include <QTimer>
|
||||
#include <QToolBar>
|
||||
#include <QVBoxLayout>
|
||||
#include <QWidgetAction>
|
||||
#include <QtCore/qbuffer.h>
|
||||
#include <dust3d/base/debug.h>
|
||||
#include <dust3d/base/ds3_file.h>
|
||||
#include <dust3d/base/snapshot.h>
|
||||
#include <dust3d/base/snapshot_xml.h>
|
||||
#include <dust3d/base/debug.h>
|
||||
#include "document_window.h"
|
||||
#include "skeleton_graphics_widget.h"
|
||||
#include "theme.h"
|
||||
#include "log_browser.h"
|
||||
#include "about_widget.h"
|
||||
#include "version.h"
|
||||
#include "glb_file.h"
|
||||
#include "part_manage_widget.h"
|
||||
#include "material_manage_widget.h"
|
||||
#include "image_forever.h"
|
||||
#include "spinnable_toolbar_icon.h"
|
||||
#include "fbx_file.h"
|
||||
#include "float_number_widget.h"
|
||||
#include "updates_check_widget.h"
|
||||
#include "document_saver.h"
|
||||
#include "document.h"
|
||||
#include "preferences.h"
|
||||
#include "flow_layout.h"
|
||||
#include "cut_face_preview.h"
|
||||
#include "horizontal_line_widget.h"
|
||||
#include "texture_generator.h"
|
||||
#include <map>
|
||||
|
||||
LogBrowser *g_logBrowser = nullptr;
|
||||
std::map<DocumentWindow *, dust3d::Uuid> g_documentWindows;
|
||||
QTextBrowser *g_acknowlegementsWidget = nullptr;
|
||||
AboutWidget *g_aboutWidget = nullptr;
|
||||
QTextBrowser *g_contributorsWidget = nullptr;
|
||||
QTextBrowser *g_supportersWidget = nullptr;
|
||||
UpdatesCheckWidget *g_updatesCheckWidget = nullptr;
|
||||
LogBrowser* g_logBrowser = nullptr;
|
||||
std::map<DocumentWindow*, dust3d::Uuid> g_documentWindows;
|
||||
QTextBrowser* g_acknowlegementsWidget = nullptr;
|
||||
AboutWidget* g_aboutWidget = nullptr;
|
||||
QTextBrowser* g_contributorsWidget = nullptr;
|
||||
QTextBrowser* g_supportersWidget = nullptr;
|
||||
UpdatesCheckWidget* g_updatesCheckWidget = nullptr;
|
||||
|
||||
void outputMessage(QtMsgType type, const QMessageLogContext &context, const QString &msg)
|
||||
void outputMessage(QtMsgType type, const QMessageLogContext& context, const QString& msg)
|
||||
{
|
||||
if (g_logBrowser)
|
||||
g_logBrowser->outputMessage(type, msg, context.file, context.line);
|
||||
}
|
||||
|
||||
void ensureFileExtension(QString* filename, const QString extension) {
|
||||
void ensureFileExtension(QString* filename, const QString extension)
|
||||
{
|
||||
if (!filename->endsWith(extension)) {
|
||||
filename->append(extension);
|
||||
}
|
||||
}
|
||||
|
||||
const std::map<DocumentWindow *, dust3d::Uuid> &DocumentWindow::documentWindows()
|
||||
const std::map<DocumentWindow*, dust3d::Uuid>& DocumentWindow::documentWindows()
|
||||
{
|
||||
return g_documentWindows;
|
||||
}
|
||||
|
||||
Document *DocumentWindow::document()
|
||||
Document* DocumentWindow::document()
|
||||
{
|
||||
return m_document;
|
||||
}
|
||||
|
@ -160,21 +161,21 @@ DocumentWindow::DocumentWindow()
|
|||
qInstallMessageHandler(&outputMessage);
|
||||
}
|
||||
|
||||
g_documentWindows.insert({this, dust3d::Uuid::createUuid()});
|
||||
g_documentWindows.insert({ this, dust3d::Uuid::createUuid() });
|
||||
|
||||
m_document = new Document;
|
||||
|
||||
SkeletonGraphicsWidget *canvasGraphicsWidget = new SkeletonGraphicsWidget(m_document);
|
||||
SkeletonGraphicsWidget* canvasGraphicsWidget = new SkeletonGraphicsWidget(m_document);
|
||||
m_canvasGraphicsWidget = canvasGraphicsWidget;
|
||||
|
||||
QVBoxLayout *toolButtonLayout = new QVBoxLayout;
|
||||
QVBoxLayout* toolButtonLayout = new QVBoxLayout;
|
||||
toolButtonLayout->setSpacing(0);
|
||||
toolButtonLayout->setContentsMargins(5, 10, 4, 0);
|
||||
|
||||
ToolbarButton *addButton = new ToolbarButton(":/resources/toolbar_add.svg");
|
||||
ToolbarButton* addButton = new ToolbarButton(":/resources/toolbar_add.svg");
|
||||
addButton->setToolTip(tr("Add node to canvas"));
|
||||
|
||||
ToolbarButton *selectButton = new ToolbarButton(":/resources/toolbar_pointer.svg");
|
||||
ToolbarButton* selectButton = new ToolbarButton(":/resources/toolbar_pointer.svg");
|
||||
selectButton->setToolTip(tr("Select node on canvas"));
|
||||
|
||||
m_xLockButton = new ToolbarButton();
|
||||
|
@ -219,17 +220,16 @@ DocumentWindow::DocumentWindow()
|
|||
toolButtonLayout->addSpacing(20);
|
||||
toolButtonLayout->addWidget(m_inprogressIndicator);
|
||||
|
||||
|
||||
QLabel *verticalLogoLabel = new QLabel;
|
||||
QLabel* verticalLogoLabel = new QLabel;
|
||||
QImage verticalLogoImage;
|
||||
verticalLogoImage.load(":/resources/dust3d-vertical.png");
|
||||
verticalLogoLabel->setPixmap(QPixmap::fromImage(verticalLogoImage));
|
||||
|
||||
QHBoxLayout *logoLayout = new QHBoxLayout;
|
||||
QHBoxLayout* logoLayout = new QHBoxLayout;
|
||||
logoLayout->addWidget(verticalLogoLabel);
|
||||
logoLayout->setContentsMargins(0, 0, 0, 0);
|
||||
|
||||
QVBoxLayout *mainLeftLayout = new QVBoxLayout;
|
||||
QVBoxLayout* mainLeftLayout = new QVBoxLayout;
|
||||
mainLeftLayout->setSpacing(0);
|
||||
mainLeftLayout->setContentsMargins(0, 0, 0, 0);
|
||||
mainLeftLayout->addLayout(toolButtonLayout);
|
||||
|
@ -237,9 +237,9 @@ DocumentWindow::DocumentWindow()
|
|||
mainLeftLayout->addLayout(logoLayout);
|
||||
mainLeftLayout->addSpacing(10);
|
||||
|
||||
GraphicsContainerWidget *containerWidget = new GraphicsContainerWidget;
|
||||
GraphicsContainerWidget* containerWidget = new GraphicsContainerWidget;
|
||||
containerWidget->setGraphicsWidget(canvasGraphicsWidget);
|
||||
QGridLayout *containerLayout = new QGridLayout;
|
||||
QGridLayout* containerLayout = new QGridLayout;
|
||||
containerLayout->setSpacing(0);
|
||||
containerLayout->setContentsMargins(1, 0, 0, 0);
|
||||
containerLayout->addWidget(canvasGraphicsWidget);
|
||||
|
@ -265,22 +265,22 @@ DocumentWindow::DocumentWindow()
|
|||
|
||||
setTabPosition(Qt::RightDockWidgetArea, QTabWidget::East);
|
||||
|
||||
QDockWidget *partsDocker = new QDockWidget(tr("Parts"), this);
|
||||
QDockWidget* partsDocker = new QDockWidget(tr("Parts"), this);
|
||||
partsDocker->setAllowedAreas(Qt::RightDockWidgetArea);
|
||||
m_partManageWidget = new PartManageWidget(m_document);
|
||||
partsDocker->setWidget(m_partManageWidget);
|
||||
addDockWidget(Qt::RightDockWidgetArea, partsDocker);
|
||||
|
||||
QDockWidget *materialDocker = new QDockWidget(tr("Materials"), this);
|
||||
QDockWidget* materialDocker = new QDockWidget(tr("Materials"), this);
|
||||
materialDocker->setAllowedAreas(Qt::RightDockWidgetArea);
|
||||
MaterialManageWidget *materialManageWidget = new MaterialManageWidget(m_document, materialDocker);
|
||||
MaterialManageWidget* materialManageWidget = new MaterialManageWidget(m_document, materialDocker);
|
||||
materialDocker->setWidget(materialManageWidget);
|
||||
connect(materialManageWidget, &MaterialManageWidget::registerDialog, this, &DocumentWindow::registerDialog);
|
||||
connect(materialManageWidget, &MaterialManageWidget::unregisterDialog, this, &DocumentWindow::unregisterDialog);
|
||||
addDockWidget(Qt::RightDockWidgetArea, materialDocker);
|
||||
connect(materialDocker, &QDockWidget::topLevelChanged, [=](bool topLevel) {
|
||||
Q_UNUSED(topLevel);
|
||||
for (const auto &material: m_document->materialMap)
|
||||
for (const auto& material : m_document->materialMap)
|
||||
emit m_document->materialPreviewChanged(material.first);
|
||||
});
|
||||
|
||||
|
@ -288,28 +288,28 @@ DocumentWindow::DocumentWindow()
|
|||
|
||||
partsDocker->raise();
|
||||
|
||||
QWidget *titleBarWidget = new QWidget;
|
||||
QWidget* titleBarWidget = new QWidget;
|
||||
titleBarWidget->setFixedHeight(1);
|
||||
|
||||
QHBoxLayout *titleBarLayout = new QHBoxLayout;
|
||||
QHBoxLayout* titleBarLayout = new QHBoxLayout;
|
||||
titleBarLayout->addStretch();
|
||||
titleBarWidget->setLayout(titleBarLayout);
|
||||
|
||||
QVBoxLayout *canvasLayout = new QVBoxLayout;
|
||||
QVBoxLayout* canvasLayout = new QVBoxLayout;
|
||||
canvasLayout->setSpacing(0);
|
||||
canvasLayout->setContentsMargins(0, 0, 0, 0);
|
||||
canvasLayout->addWidget(titleBarWidget);
|
||||
canvasLayout->addWidget(containerWidget);
|
||||
canvasLayout->setStretch(1, 1);
|
||||
|
||||
QHBoxLayout *mainLayout = new QHBoxLayout;
|
||||
QHBoxLayout* mainLayout = new QHBoxLayout;
|
||||
mainLayout->setSpacing(0);
|
||||
mainLayout->setContentsMargins(0, 0, 0, 0);
|
||||
mainLayout->addLayout(mainLeftLayout);
|
||||
mainLayout->addLayout(canvasLayout);
|
||||
mainLayout->addSpacing(3);
|
||||
|
||||
QWidget *centralWidget = new QWidget;
|
||||
QWidget* centralWidget = new QWidget;
|
||||
centralWidget->setLayout(mainLayout);
|
||||
|
||||
setCentralWidget(centralWidget);
|
||||
|
@ -322,12 +322,12 @@ DocumentWindow::DocumentWindow()
|
|||
m_fileMenu->addAction(m_newWindowAction);
|
||||
|
||||
m_newDocumentAction = m_fileMenu->addAction(tr("&New"),
|
||||
this, &DocumentWindow::newDocument,
|
||||
QKeySequence::New);
|
||||
this, &DocumentWindow::newDocument,
|
||||
QKeySequence::New);
|
||||
|
||||
m_openAction = m_fileMenu->addAction(tr("&Open..."),
|
||||
this, &DocumentWindow::open,
|
||||
QKeySequence::Open);
|
||||
this, &DocumentWindow::open,
|
||||
QKeySequence::Open);
|
||||
|
||||
m_openExampleMenu = new QMenu(tr("Open Example"));
|
||||
std::vector<QString> exampleModels = {
|
||||
|
@ -340,8 +340,8 @@ DocumentWindow::DocumentWindow()
|
|||
"Screwdriver",
|
||||
"Seagull"
|
||||
};
|
||||
for (const auto &model: exampleModels) {
|
||||
QAction *openModelAction = new QAction(model, this);
|
||||
for (const auto& model : exampleModels) {
|
||||
QAction* openModelAction = new QAction(model, this);
|
||||
connect(openModelAction, &QAction::triggered, this, [this, model]() {
|
||||
openExample("model-" + model.toLower().replace(QChar(' '), QChar('-')) + ".ds3");
|
||||
});
|
||||
|
@ -351,8 +351,8 @@ DocumentWindow::DocumentWindow()
|
|||
m_fileMenu->addMenu(m_openExampleMenu);
|
||||
|
||||
m_saveAction = m_fileMenu->addAction(tr("&Save"),
|
||||
this, &DocumentWindow::save,
|
||||
QKeySequence::Save);
|
||||
this, &DocumentWindow::save,
|
||||
QKeySequence::Save);
|
||||
|
||||
m_saveAsAction = new QAction(tr("Save As..."), this);
|
||||
connect(m_saveAsAction, &QAction::triggered, this, &DocumentWindow::saveAs, Qt::QueuedConnection);
|
||||
|
@ -385,7 +385,7 @@ DocumentWindow::DocumentWindow()
|
|||
m_fileMenu->addSeparator();
|
||||
|
||||
for (int i = 0; i < Preferences::instance().maxRecentFiles(); ++i) {
|
||||
QAction *action = new QAction(this);
|
||||
QAction* action = new QAction(this);
|
||||
action->setVisible(false);
|
||||
connect(action, &QAction::triggered, this, &DocumentWindow::openRecentFile, Qt::QueuedConnection);
|
||||
m_recentFileActions.push_back(action);
|
||||
|
@ -396,8 +396,8 @@ DocumentWindow::DocumentWindow()
|
|||
updateRecentFileActions();
|
||||
|
||||
m_quitAction = m_fileMenu->addAction(tr("&Quit"),
|
||||
this, &DocumentWindow::close,
|
||||
QKeySequence::Quit);
|
||||
this, &DocumentWindow::close,
|
||||
QKeySequence::Quit);
|
||||
|
||||
connect(m_fileMenu, &QMenu::aboutToShow, [=]() {
|
||||
m_exportAsObjAction->setEnabled(m_canvasGraphicsWidget->hasItems());
|
||||
|
@ -439,16 +439,16 @@ DocumentWindow::DocumentWindow()
|
|||
});
|
||||
m_windowMenu->addAction(m_showMaterialsAction);
|
||||
|
||||
QMenu *dialogsMenu = m_windowMenu->addMenu(tr("Dialogs"));
|
||||
QMenu* dialogsMenu = m_windowMenu->addMenu(tr("Dialogs"));
|
||||
connect(dialogsMenu, &QMenu::aboutToShow, [=]() {
|
||||
dialogsMenu->clear();
|
||||
if (this->m_dialogs.empty()) {
|
||||
QAction *action = dialogsMenu->addAction(tr("None"));
|
||||
QAction* action = dialogsMenu->addAction(tr("None"));
|
||||
action->setEnabled(false);
|
||||
return;
|
||||
}
|
||||
for (const auto &dialog: this->m_dialogs) {
|
||||
QAction *action = dialogsMenu->addAction(dialog->windowTitle());
|
||||
for (const auto& dialog : this->m_dialogs) {
|
||||
QAction* action = dialogsMenu->addAction(dialog->windowTitle());
|
||||
connect(action, &QAction::triggered, [=]() {
|
||||
dialog->show();
|
||||
dialog->raise();
|
||||
|
@ -659,7 +659,7 @@ DocumentWindow::DocumentWindow()
|
|||
connect(m_document, &Document::turnaroundChanged, this, &DocumentWindow::documentChanged);
|
||||
connect(m_document, &Document::optionsChanged, this, &DocumentWindow::documentChanged);
|
||||
|
||||
connect(m_modelRenderWidget, &ModelWidget::customContextMenuRequested, [=](const QPoint &pos) {
|
||||
connect(m_modelRenderWidget, &ModelWidget::customContextMenuRequested, [=](const QPoint& pos) {
|
||||
canvasGraphicsWidget->showContextMenu(canvasGraphicsWidget->mapFromGlobal(m_modelRenderWidget->mapToGlobal(pos)));
|
||||
});
|
||||
|
||||
|
@ -681,10 +681,10 @@ DocumentWindow::DocumentWindow()
|
|||
|
||||
connect(this, &DocumentWindow::initialized, m_document, &Document::uiReady);
|
||||
|
||||
QTimer *timer = new QTimer(this);
|
||||
QTimer* timer = new QTimer(this);
|
||||
timer->setInterval(250);
|
||||
connect(timer, &QTimer::timeout, [=] {
|
||||
QWidget *focusedWidget = QApplication::focusWidget();
|
||||
QWidget* focusedWidget = QApplication::focusWidget();
|
||||
if (nullptr == focusedWidget && isActiveWindow())
|
||||
canvasGraphicsWidget->setFocus();
|
||||
});
|
||||
|
@ -693,11 +693,7 @@ DocumentWindow::DocumentWindow()
|
|||
|
||||
void DocumentWindow::updateInprogressIndicator()
|
||||
{
|
||||
bool inprogress = m_document->isMeshGenerating() ||
|
||||
m_document->isPostProcessing() ||
|
||||
m_document->isTextureGenerating() ||
|
||||
nullptr != m_componentPreviewImagesGenerator ||
|
||||
nullptr != m_componentPreviewImagesDecorator;
|
||||
bool inprogress = m_document->isMeshGenerating() || m_document->isPostProcessing() || m_document->isTextureGenerating() || nullptr != m_componentPreviewImagesGenerator || nullptr != m_componentPreviewImagesDecorator;
|
||||
if (inprogress == m_inprogressIndicator->isSpinning())
|
||||
return;
|
||||
m_inprogressIndicator->showSpinner(inprogress);
|
||||
|
@ -711,9 +707,9 @@ void DocumentWindow::toggleRotation()
|
|||
m_canvasGraphicsWidget->setRotated(!m_canvasGraphicsWidget->rotated());
|
||||
}
|
||||
|
||||
DocumentWindow *DocumentWindow::createDocumentWindow()
|
||||
DocumentWindow* DocumentWindow::createDocumentWindow()
|
||||
{
|
||||
DocumentWindow *documentWindow = new DocumentWindow();
|
||||
DocumentWindow* documentWindow = new DocumentWindow();
|
||||
documentWindow->setAttribute(Qt::WA_DeleteOnClose);
|
||||
|
||||
QSize size = Preferences::instance().documentWindowSize();
|
||||
|
@ -727,9 +723,9 @@ DocumentWindow *DocumentWindow::createDocumentWindow()
|
|||
return documentWindow;
|
||||
}
|
||||
|
||||
void DocumentWindow::closeEvent(QCloseEvent *event)
|
||||
void DocumentWindow::closeEvent(QCloseEvent* event)
|
||||
{
|
||||
if (! m_documentSaved) {
|
||||
if (!m_documentSaved) {
|
||||
QMessageBox::StandardButton answer = QMessageBox::question(this,
|
||||
APP_NAME,
|
||||
tr("Do you really want to close while there are unsaved changes?"),
|
||||
|
@ -749,7 +745,7 @@ void DocumentWindow::closeEvent(QCloseEvent *event)
|
|||
event->accept();
|
||||
}
|
||||
|
||||
void DocumentWindow::setCurrentFilename(const QString &filename)
|
||||
void DocumentWindow::setCurrentFilename(const QString& filename)
|
||||
{
|
||||
m_currentFilename = filename;
|
||||
m_documentSaved = true;
|
||||
|
@ -796,7 +792,7 @@ void DocumentWindow::newDocument()
|
|||
void DocumentWindow::saveAs()
|
||||
{
|
||||
QString filename = QFileDialog::getSaveFileName(this, QString(), QString(),
|
||||
tr("Dust3D Document (*.ds3)"));
|
||||
tr("Dust3D Document (*.ds3)"));
|
||||
if (filename.isEmpty()) {
|
||||
return;
|
||||
}
|
||||
|
@ -806,7 +802,7 @@ void DocumentWindow::saveAs()
|
|||
|
||||
void DocumentWindow::saveAll()
|
||||
{
|
||||
for (auto &it: g_documentWindows) {
|
||||
for (auto& it : g_documentWindows) {
|
||||
it.first->save();
|
||||
}
|
||||
}
|
||||
|
@ -866,7 +862,7 @@ DocumentWindow::~DocumentWindow()
|
|||
delete m_document;
|
||||
}
|
||||
|
||||
void DocumentWindow::showEvent(QShowEvent *event)
|
||||
void DocumentWindow::showEvent(QShowEvent* event)
|
||||
{
|
||||
QMainWindow::showEvent(event);
|
||||
if (m_firstShow) {
|
||||
|
@ -878,7 +874,7 @@ void DocumentWindow::showEvent(QShowEvent *event)
|
|||
}
|
||||
}
|
||||
|
||||
void DocumentWindow::mousePressEvent(QMouseEvent *event)
|
||||
void DocumentWindow::mousePressEvent(QMouseEvent* event)
|
||||
{
|
||||
QMainWindow::mousePressEvent(event);
|
||||
}
|
||||
|
@ -886,7 +882,8 @@ void DocumentWindow::mousePressEvent(QMouseEvent *event)
|
|||
void DocumentWindow::changeTurnaround()
|
||||
{
|
||||
QString fileName = QFileDialog::getOpenFileName(this, QString(), QString(),
|
||||
tr("Image Files (*.png *.jpg *.bmp)")).trimmed();
|
||||
tr("Image Files (*.png *.jpg *.bmp)"))
|
||||
.trimmed();
|
||||
if (fileName.isEmpty())
|
||||
return;
|
||||
QImage image;
|
||||
|
@ -900,13 +897,13 @@ void DocumentWindow::save()
|
|||
saveTo(m_currentFilename);
|
||||
}
|
||||
|
||||
void DocumentWindow::saveTo(const QString &saveAsFilename)
|
||||
void DocumentWindow::saveTo(const QString& saveAsFilename)
|
||||
{
|
||||
QString filename = saveAsFilename;
|
||||
|
||||
if (filename.isEmpty()) {
|
||||
filename = QFileDialog::getSaveFileName(this, QString(), QString(),
|
||||
tr("Dust3D Document (*.ds3)"));
|
||||
tr("Dust3D Document (*.ds3)"));
|
||||
if (filename.isEmpty()) {
|
||||
return;
|
||||
}
|
||||
|
@ -918,14 +915,13 @@ void DocumentWindow::saveTo(const QString &saveAsFilename)
|
|||
m_document->toSnapshot(&snapshot);
|
||||
if (DocumentSaver::save(&filename,
|
||||
&snapshot,
|
||||
(!m_document->turnaround.isNull() && m_document->turnaroundPngByteArray.size() > 0) ?
|
||||
&m_document->turnaroundPngByteArray : nullptr)) {
|
||||
(!m_document->turnaround.isNull() && m_document->turnaroundPngByteArray.size() > 0) ? &m_document->turnaroundPngByteArray : nullptr)) {
|
||||
setCurrentFilename(filename);
|
||||
}
|
||||
QApplication::restoreOverrideCursor();
|
||||
}
|
||||
|
||||
void DocumentWindow::openPathAs(const QString &path, const QString &asName)
|
||||
void DocumentWindow::openPathAs(const QString& path, const QString& asName)
|
||||
{
|
||||
QApplication::setOverrideCursor(Qt::WaitCursor);
|
||||
|
||||
|
@ -938,9 +934,9 @@ void DocumentWindow::openPathAs(const QString &path, const QString &asName)
|
|||
file.open(QFile::ReadOnly);
|
||||
QByteArray fileData = file.readAll();
|
||||
|
||||
dust3d::Ds3FileReader ds3Reader((const std::uint8_t *)fileData.data(), fileData.size());
|
||||
dust3d::Ds3FileReader ds3Reader((const std::uint8_t*)fileData.data(), fileData.size());
|
||||
for (int i = 0; i < (int)ds3Reader.items().size(); ++i) {
|
||||
const dust3d::Ds3ReaderItem &item = ds3Reader.items()[i];
|
||||
const dust3d::Ds3ReaderItem& item = ds3Reader.items()[i];
|
||||
qDebug() << "[" << i << "]item.name:" << item.name << "item.type:" << item.type;
|
||||
if (item.type == "asset") {
|
||||
if (dust3d::String::startsWith(item.name, "images/")) {
|
||||
|
@ -958,13 +954,13 @@ void DocumentWindow::openPathAs(const QString &path, const QString &asName)
|
|||
}
|
||||
|
||||
for (int i = 0; i < (int)ds3Reader.items().size(); ++i) {
|
||||
const dust3d::Ds3ReaderItem &item = ds3Reader.items()[i];
|
||||
const dust3d::Ds3ReaderItem& item = ds3Reader.items()[i];
|
||||
if (item.type == "model") {
|
||||
std::vector<std::uint8_t> data;
|
||||
ds3Reader.loadItem(item.name, &data);
|
||||
data.push_back('\0');
|
||||
dust3d::Snapshot snapshot;
|
||||
loadSnapshotFromXmlString(&snapshot, (char *)data.data());
|
||||
loadSnapshotFromXmlString(&snapshot, (char*)data.data());
|
||||
m_document->fromSnapshot(snapshot);
|
||||
m_document->saveSnapshot();
|
||||
} else if (item.type == "asset") {
|
||||
|
@ -980,14 +976,14 @@ void DocumentWindow::openPathAs(const QString &path, const QString &asName)
|
|||
|
||||
if (!asName.isEmpty()) {
|
||||
Preferences::instance().setCurrentFile(path);
|
||||
for (auto &it: g_documentWindows) {
|
||||
for (auto& it : g_documentWindows) {
|
||||
it.first->updateRecentFileActions();
|
||||
}
|
||||
}
|
||||
setCurrentFilename(asName);
|
||||
}
|
||||
|
||||
void DocumentWindow::openExample(const QString &modelName)
|
||||
void DocumentWindow::openExample(const QString& modelName)
|
||||
{
|
||||
if (!m_documentSaved) {
|
||||
QMessageBox::StandardButton answer = QMessageBox::question(this,
|
||||
|
@ -1025,7 +1021,7 @@ void DocumentWindow::open()
|
|||
void DocumentWindow::exportObjResult()
|
||||
{
|
||||
QString filename = QFileDialog::getSaveFileName(this, QString(), QString(),
|
||||
tr("Wavefront (*.obj)"));
|
||||
tr("Wavefront (*.obj)"));
|
||||
if (filename.isEmpty()) {
|
||||
return;
|
||||
}
|
||||
|
@ -1033,10 +1029,10 @@ void DocumentWindow::exportObjResult()
|
|||
exportObjToFilename(filename);
|
||||
}
|
||||
|
||||
void DocumentWindow::exportObjToFilename(const QString &filename)
|
||||
void DocumentWindow::exportObjToFilename(const QString& filename)
|
||||
{
|
||||
QApplication::setOverrideCursor(Qt::WaitCursor);
|
||||
ModelMesh *resultMesh = m_document->takeResultMesh();
|
||||
ModelMesh* resultMesh = m_document->takeResultMesh();
|
||||
if (nullptr != resultMesh) {
|
||||
resultMesh->exportAsObj(filename);
|
||||
delete resultMesh;
|
||||
|
@ -1047,7 +1043,7 @@ void DocumentWindow::exportObjToFilename(const QString &filename)
|
|||
void DocumentWindow::exportFbxResult()
|
||||
{
|
||||
QString filename = QFileDialog::getSaveFileName(this, QString(), QString(),
|
||||
tr("Autodesk FBX (*.fbx)"));
|
||||
tr("Autodesk FBX (*.fbx)"));
|
||||
if (filename.isEmpty()) {
|
||||
return;
|
||||
}
|
||||
|
@ -1055,7 +1051,7 @@ void DocumentWindow::exportFbxResult()
|
|||
exportFbxToFilename(filename);
|
||||
}
|
||||
|
||||
void DocumentWindow::exportFbxToFilename(const QString &filename)
|
||||
void DocumentWindow::exportFbxToFilename(const QString& filename)
|
||||
{
|
||||
if (!m_document->isExportReady()) {
|
||||
qDebug() << "Export but document is not export ready";
|
||||
|
@ -1077,7 +1073,7 @@ void DocumentWindow::exportFbxToFilename(const QString &filename)
|
|||
void DocumentWindow::exportGlbResult()
|
||||
{
|
||||
QString filename = QFileDialog::getSaveFileName(this, QString(), QString(),
|
||||
tr("glTF Binary Format (*.glb)"));
|
||||
tr("glTF Binary Format (*.glb)"));
|
||||
if (filename.isEmpty()) {
|
||||
return;
|
||||
}
|
||||
|
@ -1085,7 +1081,7 @@ void DocumentWindow::exportGlbResult()
|
|||
exportGlbToFilename(filename);
|
||||
}
|
||||
|
||||
void DocumentWindow::exportGlbToFilename(const QString &filename)
|
||||
void DocumentWindow::exportGlbToFilename(const QString& filename)
|
||||
{
|
||||
if (!m_document->isExportReady()) {
|
||||
qDebug() << "Export but document is not export ready";
|
||||
|
@ -1093,10 +1089,9 @@ void DocumentWindow::exportGlbToFilename(const QString &filename)
|
|||
}
|
||||
QApplication::setOverrideCursor(Qt::WaitCursor);
|
||||
dust3d::Object skeletonResult = m_document->currentPostProcessedObject();
|
||||
QImage *textureMetalnessRoughnessAmbientOcclusionImage =
|
||||
TextureGenerator::combineMetalnessRoughnessAmbientOcclusionImages(m_document->textureMetalnessImage,
|
||||
m_document->textureRoughnessImage,
|
||||
m_document->textureAmbientOcclusionImage);
|
||||
QImage* textureMetalnessRoughnessAmbientOcclusionImage = TextureGenerator::combineMetalnessRoughnessAmbientOcclusionImages(m_document->textureMetalnessImage,
|
||||
m_document->textureRoughnessImage,
|
||||
m_document->textureAmbientOcclusionImage);
|
||||
GlbFileWriter glbFileWriter(skeletonResult, filename,
|
||||
m_document->textureImage, m_document->textureNormalImage, textureMetalnessRoughnessAmbientOcclusionImage);
|
||||
glbFileWriter.save();
|
||||
|
@ -1136,17 +1131,17 @@ void DocumentWindow::updateRadiusLockButtonState()
|
|||
m_radiusLockButton->setIcon(":/resources/toolbar_radius.svg");
|
||||
}
|
||||
|
||||
void DocumentWindow::registerDialog(QWidget *widget)
|
||||
void DocumentWindow::registerDialog(QWidget* widget)
|
||||
{
|
||||
m_dialogs.push_back(widget);
|
||||
}
|
||||
|
||||
void DocumentWindow::unregisterDialog(QWidget *widget)
|
||||
void DocumentWindow::unregisterDialog(QWidget* widget)
|
||||
{
|
||||
m_dialogs.erase(std::remove(m_dialogs.begin(), m_dialogs.end(), widget), m_dialogs.end());
|
||||
}
|
||||
|
||||
void DocumentWindow::setExportWaitingList(const QStringList &filenames)
|
||||
void DocumentWindow::setExportWaitingList(const QStringList& filenames)
|
||||
{
|
||||
m_waitingForExportToFilenames = filenames;
|
||||
}
|
||||
|
@ -1160,7 +1155,7 @@ void DocumentWindow::checkExportWaitingList()
|
|||
m_waitingForExportToFilenames.clear();
|
||||
|
||||
bool isSuccessful = m_document->isMeshGenerationSucceed();
|
||||
for (const auto &filename: list) {
|
||||
for (const auto& filename : list) {
|
||||
if (filename.endsWith(".obj")) {
|
||||
exportObjToFilename(filename);
|
||||
emit waitingExportFinished(filename, isSuccessful);
|
||||
|
@ -1185,10 +1180,10 @@ void DocumentWindow::generateComponentPreviewImages()
|
|||
|
||||
m_isComponentPreviewImagesObsolete = false;
|
||||
|
||||
QThread *thread = new QThread;
|
||||
QThread* thread = new QThread;
|
||||
|
||||
m_componentPreviewImagesGenerator = new MeshPreviewImagesGenerator(new ModelOffscreenRender(m_modelRenderWidget->format()));
|
||||
for (auto &component: m_document->componentMap) {
|
||||
for (auto& component : m_document->componentMap) {
|
||||
if (!component.second.isPreviewMeshObsolete)
|
||||
continue;
|
||||
component.second.isPreviewMeshObsolete = false;
|
||||
|
@ -1209,7 +1204,7 @@ void DocumentWindow::componentPreviewImagesReady()
|
|||
std::unique_ptr<std::map<dust3d::Uuid, QImage>> componentImages;
|
||||
componentImages.reset(m_componentPreviewImagesGenerator->takeImages());
|
||||
if (nullptr != componentImages) {
|
||||
for (const auto &it: *componentImages) {
|
||||
for (const auto& it : *componentImages) {
|
||||
m_document->setComponentPreviewImage(it.first, std::make_unique<QImage>(std::move(it.second)));
|
||||
}
|
||||
}
|
||||
|
@ -1234,10 +1229,10 @@ void DocumentWindow::decorateComponentPreviewImages()
|
|||
|
||||
m_isComponentPreviewImageDecorationsObsolete = false;
|
||||
|
||||
QThread *thread = new QThread;
|
||||
QThread* thread = new QThread;
|
||||
|
||||
auto previewInputs = std::make_unique<std::vector<ComponentPreviewImagesDecorator::PreviewInput>>();
|
||||
for (auto &component: m_document->componentMap) {
|
||||
for (auto& component : m_document->componentMap) {
|
||||
if (!component.second.isPreviewImageDecorationObsolete)
|
||||
continue;
|
||||
component.second.isPreviewImageDecorationObsolete = false;
|
||||
|
@ -1246,8 +1241,7 @@ void DocumentWindow::decorateComponentPreviewImages()
|
|||
previewInputs->emplace_back(ComponentPreviewImagesDecorator::PreviewInput {
|
||||
component.first,
|
||||
std::make_unique<QImage>(*component.second.previewImage),
|
||||
!component.second.childrenIds.empty()
|
||||
});
|
||||
!component.second.childrenIds.empty() });
|
||||
}
|
||||
m_componentPreviewImagesDecorator = std::make_unique<ComponentPreviewImagesDecorator>(std::move(previewInputs));
|
||||
m_componentPreviewImagesDecorator->moveToThread(thread);
|
||||
|
@ -1264,7 +1258,7 @@ void DocumentWindow::componentPreviewImageDecorationsReady()
|
|||
{
|
||||
auto resultImages = m_componentPreviewImagesDecorator->takeResultImages();
|
||||
if (nullptr != resultImages) {
|
||||
for (auto &it: *resultImages) {
|
||||
for (auto& it : *resultImages) {
|
||||
if (nullptr == it.second)
|
||||
continue;
|
||||
m_document->setComponentPreviewPixmap(it.first, QPixmap::fromImage(*it.second));
|
||||
|
@ -1279,26 +1273,26 @@ void DocumentWindow::componentPreviewImageDecorationsReady()
|
|||
updateInprogressIndicator();
|
||||
}
|
||||
|
||||
ModelWidget *DocumentWindow::modelWidget()
|
||||
ModelWidget* DocumentWindow::modelWidget()
|
||||
{
|
||||
return m_modelRenderWidget;
|
||||
}
|
||||
|
||||
QShortcut *DocumentWindow::createShortcut(QKeySequence key)
|
||||
QShortcut* DocumentWindow::createShortcut(QKeySequence key)
|
||||
{
|
||||
auto shortcutIt = m_shortcutMap.find(key);
|
||||
if (shortcutIt != m_shortcutMap.end())
|
||||
return shortcutIt->second;
|
||||
QShortcut *shortcut = new QShortcut(this);
|
||||
QShortcut* shortcut = new QShortcut(this);
|
||||
shortcut->setKey(key);
|
||||
m_shortcutMap.insert({key, shortcut});
|
||||
m_shortcutMap.insert({ key, shortcut });
|
||||
return shortcut;
|
||||
}
|
||||
|
||||
#define defineShortcut(keyVal, widget, funcName) \
|
||||
#define defineShortcut(keyVal, widget, funcName) \
|
||||
QObject::connect(createShortcut(keyVal), &QShortcut::activated, widget, funcName)
|
||||
|
||||
void DocumentWindow::initializeToolShortcuts(SkeletonGraphicsWidget *graphicsWidget)
|
||||
void DocumentWindow::initializeToolShortcuts(SkeletonGraphicsWidget* graphicsWidget)
|
||||
{
|
||||
defineShortcut(Qt::Key_A, graphicsWidget, &SkeletonGraphicsWidget::shortcutAddMode);
|
||||
defineShortcut(Qt::CTRL + Qt::Key_A, graphicsWidget, &SkeletonGraphicsWidget::shortcutSelectAll);
|
||||
|
@ -1316,7 +1310,7 @@ void DocumentWindow::initializeToolShortcuts(SkeletonGraphicsWidget *graphicsWid
|
|||
defineShortcut(Qt::Key_Escape, graphicsWidget, &SkeletonGraphicsWidget::shortcutEscape);
|
||||
}
|
||||
|
||||
void DocumentWindow::initializeCanvasShortcuts(SkeletonGraphicsWidget *graphicsWidget)
|
||||
void DocumentWindow::initializeCanvasShortcuts(SkeletonGraphicsWidget* graphicsWidget)
|
||||
{
|
||||
defineShortcut(Qt::Key_Delete, graphicsWidget, &SkeletonGraphicsWidget::shortcutDelete);
|
||||
defineShortcut(Qt::Key_Backspace, graphicsWidget, &SkeletonGraphicsWidget::shortcutDelete);
|
||||
|
@ -1365,7 +1359,7 @@ void DocumentWindow::openRecentFile()
|
|||
return;
|
||||
}
|
||||
|
||||
QAction *action = qobject_cast<QAction *>(sender());
|
||||
QAction* action = qobject_cast<QAction*>(sender());
|
||||
if (action) {
|
||||
QString fileName = action->data().toString();
|
||||
openPathAs(fileName, fileName);
|
||||
|
@ -1388,7 +1382,7 @@ void DocumentWindow::updateRecentFileActions()
|
|||
m_recentFileSeparatorAction->setVisible(files.size() > 0);
|
||||
}
|
||||
|
||||
QString DocumentWindow::strippedName(const QString &fullFileName)
|
||||
QString DocumentWindow::strippedName(const QString& fullFileName)
|
||||
{
|
||||
return QFileInfo(fullFileName).fileName();
|
||||
}
|
||||
|
@ -1401,10 +1395,8 @@ bool DocumentWindow::isWorking()
|
|||
void DocumentWindow::toggleRenderColor()
|
||||
{
|
||||
m_modelRemoveColor = !m_modelRemoveColor;
|
||||
ModelMesh *mesh = nullptr;
|
||||
if (m_document->isMeshGenerating() ||
|
||||
m_document->isPostProcessing() ||
|
||||
m_document->isTextureGenerating()) {
|
||||
ModelMesh* mesh = nullptr;
|
||||
if (m_document->isMeshGenerating() || m_document->isPostProcessing() || m_document->isTextureGenerating()) {
|
||||
mesh = m_document->takeResultMesh();
|
||||
} else {
|
||||
mesh = m_document->takeResultTextureMesh();
|
||||
|
|
|
@ -1,21 +1,21 @@
|
|||
#ifndef DUST3D_APPLICATION_DOCUMENT_WINDOW_H_
|
||||
#define DUST3D_APPLICATION_DOCUMENT_WINDOW_H_
|
||||
|
||||
#include <memory>
|
||||
#include <QMainWindow>
|
||||
#include <QShowEvent>
|
||||
#include <QPushButton>
|
||||
#include <QString>
|
||||
#include <QMenu>
|
||||
#include <QAction>
|
||||
#include <map>
|
||||
#include <QStringList>
|
||||
#include <QLabel>
|
||||
#include <QShortcut>
|
||||
#include "model_widget.h"
|
||||
#include "component_preview_images_decorator.h"
|
||||
#include "graphics_container_widget.h"
|
||||
#include "mesh_preview_images_generator.h"
|
||||
#include "component_preview_images_decorator.h"
|
||||
#include "model_widget.h"
|
||||
#include <QAction>
|
||||
#include <QLabel>
|
||||
#include <QMainWindow>
|
||||
#include <QMenu>
|
||||
#include <QPushButton>
|
||||
#include <QShortcut>
|
||||
#include <QShowEvent>
|
||||
#include <QString>
|
||||
#include <QStringList>
|
||||
#include <map>
|
||||
#include <memory>
|
||||
|
||||
class Document;
|
||||
class SkeletonGraphicsWidget;
|
||||
|
@ -23,38 +23,39 @@ class PartManageWidget;
|
|||
class ToolbarButton;
|
||||
class SpinnableToolbarIcon;
|
||||
|
||||
class DocumentWindow : public QMainWindow
|
||||
{
|
||||
class DocumentWindow : public QMainWindow {
|
||||
Q_OBJECT
|
||||
signals:
|
||||
void initialized();
|
||||
void uninialized();
|
||||
void waitingExportFinished(const QString &filename, bool isSuccessful);
|
||||
void waitingExportFinished(const QString& filename, bool isSuccessful);
|
||||
void workingStatusChanged(bool isWorking);
|
||||
|
||||
public:
|
||||
DocumentWindow();
|
||||
~DocumentWindow();
|
||||
Document *document();
|
||||
ModelWidget *modelWidget();
|
||||
Document* document();
|
||||
ModelWidget* modelWidget();
|
||||
bool isWorking();
|
||||
static DocumentWindow *createDocumentWindow();
|
||||
static const std::map<DocumentWindow *, dust3d::Uuid> &documentWindows();
|
||||
static DocumentWindow* createDocumentWindow();
|
||||
static const std::map<DocumentWindow*, dust3d::Uuid>& documentWindows();
|
||||
static void showAcknowlegements();
|
||||
static void showContributors();
|
||||
static void showSupporters();
|
||||
static void showAbout();
|
||||
static size_t total();
|
||||
|
||||
protected:
|
||||
void showEvent(QShowEvent *event);
|
||||
void closeEvent(QCloseEvent *event);
|
||||
void mousePressEvent(QMouseEvent *event);
|
||||
void showEvent(QShowEvent* event);
|
||||
void closeEvent(QCloseEvent* event);
|
||||
void mousePressEvent(QMouseEvent* event);
|
||||
public slots:
|
||||
void changeTurnaround();
|
||||
void save();
|
||||
void saveTo(const QString &saveAsFilename);
|
||||
void saveTo(const QString& saveAsFilename);
|
||||
void open();
|
||||
void openExample(const QString &modelName);
|
||||
void openPathAs(const QString &path, const QString &asName);
|
||||
void openExample(const QString& modelName);
|
||||
void openPathAs(const QString& path, const QString& asName);
|
||||
void exportObjResult();
|
||||
void exportGlbResult();
|
||||
void exportFbxResult();
|
||||
|
@ -76,13 +77,13 @@ public slots:
|
|||
void updateYlockButtonState();
|
||||
void updateZlockButtonState();
|
||||
void updateRadiusLockButtonState();
|
||||
void registerDialog(QWidget *widget);
|
||||
void unregisterDialog(QWidget *widget);
|
||||
void setExportWaitingList(const QStringList &filenames);
|
||||
void registerDialog(QWidget* widget);
|
||||
void unregisterDialog(QWidget* widget);
|
||||
void setExportWaitingList(const QStringList& filenames);
|
||||
void checkExportWaitingList();
|
||||
void exportObjToFilename(const QString &filename);
|
||||
void exportFbxToFilename(const QString &filename);
|
||||
void exportGlbToFilename(const QString &filename);
|
||||
void exportObjToFilename(const QString& filename);
|
||||
void exportFbxToFilename(const QString& filename);
|
||||
void exportGlbToFilename(const QString& filename);
|
||||
void toggleRotation();
|
||||
void generateComponentPreviewImages();
|
||||
void componentPreviewImagesReady();
|
||||
|
@ -92,88 +93,88 @@ public slots:
|
|||
void openRecentFile();
|
||||
void updateRecentFileActions();
|
||||
void toggleRenderColor();
|
||||
|
||||
private:
|
||||
void setCurrentFilename(const QString &filename);
|
||||
void setCurrentFilename(const QString& filename);
|
||||
void updateTitle();
|
||||
void initializeShortcuts();
|
||||
void initializeToolShortcuts(SkeletonGraphicsWidget *graphicsWidget);
|
||||
void initializeCanvasShortcuts(SkeletonGraphicsWidget *graphicsWidget);
|
||||
QShortcut *createShortcut(QKeySequence key);
|
||||
QString strippedName(const QString &fullFileName);
|
||||
bool openFiles(const QStringList &pathList);
|
||||
void initializeToolShortcuts(SkeletonGraphicsWidget* graphicsWidget);
|
||||
void initializeCanvasShortcuts(SkeletonGraphicsWidget* graphicsWidget);
|
||||
QShortcut* createShortcut(QKeySequence key);
|
||||
QString strippedName(const QString& fullFileName);
|
||||
bool openFiles(const QStringList& pathList);
|
||||
|
||||
Document *m_document = nullptr;
|
||||
Document* m_document = nullptr;
|
||||
bool m_firstShow = true;
|
||||
bool m_documentSaved = true;
|
||||
std::vector<QWidget *> m_dialogs;
|
||||
std::vector<QWidget*> m_dialogs;
|
||||
bool m_isLastMeshGenerationSucceed = true;
|
||||
quint64 m_currentUpdatedMeshId = 0;
|
||||
QStringList m_waitingForExportToFilenames;
|
||||
|
||||
QString m_currentFilename;
|
||||
|
||||
ModelWidget *m_modelRenderWidget = nullptr;
|
||||
SkeletonGraphicsWidget *m_canvasGraphicsWidget = nullptr;
|
||||
GraphicsContainerWidget *m_graphicsContainerWidget = nullptr;
|
||||
ModelWidget* m_modelRenderWidget = nullptr;
|
||||
SkeletonGraphicsWidget* m_canvasGraphicsWidget = nullptr;
|
||||
GraphicsContainerWidget* m_graphicsContainerWidget = nullptr;
|
||||
|
||||
QMenu *m_fileMenu = nullptr;
|
||||
QAction *m_newWindowAction = nullptr;
|
||||
QAction *m_newDocumentAction = nullptr;
|
||||
QAction *m_openAction = nullptr;
|
||||
QMenu *m_openExampleMenu = nullptr;
|
||||
QAction *m_saveAction = nullptr;
|
||||
QAction *m_saveAsAction = nullptr;
|
||||
QAction *m_saveAllAction = nullptr;
|
||||
QAction *m_changeTurnaroundAction = nullptr;
|
||||
std::vector<QAction *> m_recentFileActions;
|
||||
QAction *m_recentFileSeparatorAction = nullptr;
|
||||
QAction *m_quitAction = nullptr;
|
||||
QMenu* m_fileMenu = nullptr;
|
||||
QAction* m_newWindowAction = nullptr;
|
||||
QAction* m_newDocumentAction = nullptr;
|
||||
QAction* m_openAction = nullptr;
|
||||
QMenu* m_openExampleMenu = nullptr;
|
||||
QAction* m_saveAction = nullptr;
|
||||
QAction* m_saveAsAction = nullptr;
|
||||
QAction* m_saveAllAction = nullptr;
|
||||
QAction* m_changeTurnaroundAction = nullptr;
|
||||
std::vector<QAction*> m_recentFileActions;
|
||||
QAction* m_recentFileSeparatorAction = nullptr;
|
||||
QAction* m_quitAction = nullptr;
|
||||
|
||||
QAction *m_exportAsObjAction = nullptr;
|
||||
QAction *m_exportAsGlbAction = nullptr;
|
||||
QAction *m_exportAsFbxAction = nullptr;
|
||||
QAction* m_exportAsObjAction = nullptr;
|
||||
QAction* m_exportAsGlbAction = nullptr;
|
||||
QAction* m_exportAsFbxAction = nullptr;
|
||||
|
||||
QMenu *m_viewMenu = nullptr;
|
||||
QAction *m_toggleWireframeAction = nullptr;
|
||||
QAction *m_toggleRotationAction = nullptr;
|
||||
QAction *m_toggleColorAction = nullptr;
|
||||
QMenu* m_viewMenu = nullptr;
|
||||
QAction* m_toggleWireframeAction = nullptr;
|
||||
QAction* m_toggleRotationAction = nullptr;
|
||||
QAction* m_toggleColorAction = nullptr;
|
||||
bool m_modelRemoveColor = false;
|
||||
|
||||
QMenu *m_windowMenu = nullptr;
|
||||
QAction *m_showPartsListAction = nullptr;
|
||||
QAction *m_showDebugDialogAction = nullptr;
|
||||
QAction *m_showMaterialsAction = nullptr;
|
||||
QMenu* m_windowMenu = nullptr;
|
||||
QAction* m_showPartsListAction = nullptr;
|
||||
QAction* m_showDebugDialogAction = nullptr;
|
||||
QAction* m_showMaterialsAction = nullptr;
|
||||
|
||||
QMenu *m_helpMenu = nullptr;
|
||||
QAction *m_gotoHomepageAction = nullptr;
|
||||
QAction *m_viewSourceAction = nullptr;
|
||||
QAction *m_aboutAction = nullptr;
|
||||
QAction *m_checkForUpdatesAction = nullptr;
|
||||
QAction *m_reportIssuesAction = nullptr;
|
||||
QAction *m_seeContributorsAction = nullptr;
|
||||
QAction *m_seeSupportersAction = nullptr;
|
||||
QAction *m_seeAcknowlegementsAction = nullptr;
|
||||
QAction *m_seeReferenceGuideAction = nullptr;
|
||||
QMenu* m_helpMenu = nullptr;
|
||||
QAction* m_gotoHomepageAction = nullptr;
|
||||
QAction* m_viewSourceAction = nullptr;
|
||||
QAction* m_aboutAction = nullptr;
|
||||
QAction* m_checkForUpdatesAction = nullptr;
|
||||
QAction* m_reportIssuesAction = nullptr;
|
||||
QAction* m_seeContributorsAction = nullptr;
|
||||
QAction* m_seeSupportersAction = nullptr;
|
||||
QAction* m_seeAcknowlegementsAction = nullptr;
|
||||
QAction* m_seeReferenceGuideAction = nullptr;
|
||||
|
||||
ToolbarButton *m_xLockButton = nullptr;
|
||||
ToolbarButton *m_yLockButton = nullptr;
|
||||
ToolbarButton *m_zLockButton = nullptr;
|
||||
ToolbarButton *m_radiusLockButton = nullptr;
|
||||
ToolbarButton* m_xLockButton = nullptr;
|
||||
ToolbarButton* m_yLockButton = nullptr;
|
||||
ToolbarButton* m_zLockButton = nullptr;
|
||||
ToolbarButton* m_radiusLockButton = nullptr;
|
||||
|
||||
QMetaObject::Connection m_partListDockerVisibleSwitchConnection;
|
||||
|
||||
MeshPreviewImagesGenerator *m_componentPreviewImagesGenerator = nullptr;
|
||||
MeshPreviewImagesGenerator* m_componentPreviewImagesGenerator = nullptr;
|
||||
bool m_isComponentPreviewImagesObsolete = false;
|
||||
|
||||
std::unique_ptr<ComponentPreviewImagesDecorator> m_componentPreviewImagesDecorator;
|
||||
bool m_isComponentPreviewImageDecorationsObsolete = false;
|
||||
|
||||
PartManageWidget *m_partManageWidget = nullptr;
|
||||
PartManageWidget* m_partManageWidget = nullptr;
|
||||
|
||||
SpinnableToolbarIcon *m_inprogressIndicator = nullptr;
|
||||
SpinnableToolbarIcon* m_inprogressIndicator = nullptr;
|
||||
|
||||
std::map<QKeySequence, QShortcut *> m_shortcutMap;
|
||||
std::map<QKeySequence, QShortcut*> m_shortcutMap;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
||||
|
|
|
@ -1,13 +1,13 @@
|
|||
#include "fbx_file.h"
|
||||
#include "document.h"
|
||||
#include "version.h"
|
||||
#include <QByteArray>
|
||||
#include <QDateTime>
|
||||
#include <QFileInfo>
|
||||
#include <QtCore/qbuffer.h>
|
||||
#include <QtMath>
|
||||
#include <fbxnode.h>
|
||||
#include <fbxproperty.h>
|
||||
#include <QDateTime>
|
||||
#include <QtMath>
|
||||
#include <QtCore/qbuffer.h>
|
||||
#include <QByteArray>
|
||||
#include <QFileInfo>
|
||||
#include "fbx_file.h"
|
||||
#include "version.h"
|
||||
#include "document.h"
|
||||
|
||||
using namespace fbx;
|
||||
|
||||
|
@ -27,8 +27,8 @@ void FbxFileWriter::createFbxHeader()
|
|||
headerExtension.addPropertyNode("EncryptionType", (int32_t)0);
|
||||
{
|
||||
auto currentDateTime = QDateTime::currentDateTime();
|
||||
const auto ¤tDate = currentDateTime.date();
|
||||
const auto ¤tTime = currentDateTime.time();
|
||||
const auto& currentDate = currentDateTime.date();
|
||||
const auto& currentTime = currentDateTime.time();
|
||||
|
||||
FBXNode creationTimeStamp("CreationTimeStamp");
|
||||
creationTimeStamp.addPropertyNode("Version", (int32_t)1000);
|
||||
|
@ -45,7 +45,7 @@ void FbxFileWriter::createFbxHeader()
|
|||
headerExtension.addPropertyNode("Creator", APP_NAME " " APP_HUMAN_VER);
|
||||
{
|
||||
FBXNode sceneInfo("SceneInfo");
|
||||
sceneInfo.addProperty(std::vector<uint8_t>({'G','l','o','b','a','l','I','n','f','o',0,1,'S','c','e','n','e','I','n','f','o'}), 'S');
|
||||
sceneInfo.addProperty(std::vector<uint8_t>({ 'G', 'l', 'o', 'b', 'a', 'l', 'I', 'n', 'f', 'o', 0, 1, 'S', 'c', 'e', 'n', 'e', 'I', 'n', 'f', 'o' }), 'S');
|
||||
sceneInfo.addProperty("UserData");
|
||||
sceneInfo.addPropertyNode("Type", "UserData");
|
||||
sceneInfo.addPropertyNode("Version", 100);
|
||||
|
@ -198,7 +198,7 @@ void FbxFileWriter::createCreationTime()
|
|||
|
||||
void FbxFileWriter::createFileId()
|
||||
{
|
||||
std::vector<uint8_t> fileIdBytes = {40, (uint8_t)-77, 42, (uint8_t)-21, (uint8_t)-74, 36, (uint8_t)-52, (uint8_t)-62, (uint8_t)-65, (uint8_t)-56, (uint8_t)-80, 42, (uint8_t)-87, 43, (uint8_t)-4, (uint8_t)-15};
|
||||
std::vector<uint8_t> fileIdBytes = { 40, (uint8_t)-77, 42, (uint8_t)-21, (uint8_t)-74, 36, (uint8_t)-52, (uint8_t)-62, (uint8_t)-65, (uint8_t)-56, (uint8_t)-80, 42, (uint8_t)-87, 43, (uint8_t)-4, (uint8_t)-15 };
|
||||
FBXNode fileId("FileId");
|
||||
fileId.addProperty(fileIdBytes, 'R');
|
||||
m_fbxDocument.nodes.push_back(fileId);
|
||||
|
@ -415,13 +415,13 @@ void FbxFileWriter::createReferences()
|
|||
}
|
||||
|
||||
void FbxFileWriter::createDefinitions(size_t deformerCount,
|
||||
size_t textureCount,
|
||||
size_t videoCount,
|
||||
bool hasAnimtion,
|
||||
size_t animationStackCount,
|
||||
size_t animationLayerCount,
|
||||
size_t animationCurveNodeCount,
|
||||
size_t animationCurveCount)
|
||||
size_t textureCount,
|
||||
size_t videoCount,
|
||||
bool hasAnimtion,
|
||||
size_t animationStackCount,
|
||||
size_t animationLayerCount,
|
||||
size_t animationCurveNodeCount,
|
||||
size_t animationCurveCount)
|
||||
{
|
||||
FBXNode definitions("Definitions");
|
||||
definitions.addPropertyNode("Version", (int32_t)100);
|
||||
|
@ -2198,15 +2198,15 @@ void FbxFileWriter::createDefinitions(size_t deformerCount,
|
|||
m_fbxDocument.nodes.push_back(definitions);
|
||||
}
|
||||
|
||||
FbxFileWriter::FbxFileWriter(dust3d::Object &object,
|
||||
const QString &filename,
|
||||
QImage *textureImage,
|
||||
QImage *normalImage,
|
||||
QImage *metalnessImage,
|
||||
QImage *roughnessImage,
|
||||
QImage *ambientOcclusionImage) :
|
||||
m_filename(filename),
|
||||
m_baseName(QFileInfo(m_filename).baseName())
|
||||
FbxFileWriter::FbxFileWriter(dust3d::Object& object,
|
||||
const QString& filename,
|
||||
QImage* textureImage,
|
||||
QImage* normalImage,
|
||||
QImage* metalnessImage,
|
||||
QImage* roughnessImage,
|
||||
QImage* ambientOcclusionImage)
|
||||
: m_filename(filename)
|
||||
, m_baseName(QFileInfo(m_filename).baseName())
|
||||
{
|
||||
createFbxHeader();
|
||||
createFileId();
|
||||
|
@ -2223,16 +2223,16 @@ FbxFileWriter::FbxFileWriter(dust3d::Object &object,
|
|||
FBXNode geometry("Geometry");
|
||||
int64_t geometryId = m_next64Id++;
|
||||
geometry.addProperty(geometryId);
|
||||
geometry.addProperty(std::vector<uint8_t>({'u','n','a','m','e','d','m','e','s','h',0,1,'G','e','o','m','e','t','r','y'}), 'S');
|
||||
geometry.addProperty(std::vector<uint8_t>({ 'u', 'n', 'a', 'm', 'e', 'd', 'm', 'e', 's', 'h', 0, 1, 'G', 'e', 'o', 'm', 'e', 't', 'r', 'y' }), 'S');
|
||||
geometry.addProperty("Mesh");
|
||||
std::vector<double> positions;
|
||||
for (const auto &vertex: object.vertices) {
|
||||
for (const auto& vertex : object.vertices) {
|
||||
positions.push_back((double)vertex.x());
|
||||
positions.push_back((double)vertex.y());
|
||||
positions.push_back((double)vertex.z());
|
||||
}
|
||||
std::vector<int32_t> indices;
|
||||
for (const auto &triangle: object.triangles) {
|
||||
for (const auto& triangle : object.triangles) {
|
||||
indices.push_back(triangle[0]);
|
||||
indices.push_back(triangle[1]);
|
||||
indices.push_back(triangle[2] ^ -1);
|
||||
|
@ -2248,7 +2248,7 @@ FbxFileWriter::FbxFileWriter(dust3d::Object &object,
|
|||
std::vector<double> normals;
|
||||
for (decltype(triangleVertexNormals->size()) i = 0; i < triangleVertexNormals->size(); ++i) {
|
||||
for (size_t j = 0; j < 3; ++j) {
|
||||
const auto &n = (*triangleVertexNormals)[i][j];
|
||||
const auto& n = (*triangleVertexNormals)[i][j];
|
||||
normals.push_back((double)n.x());
|
||||
normals.push_back((double)n.y());
|
||||
normals.push_back((double)n.z());
|
||||
|
@ -2269,7 +2269,7 @@ FbxFileWriter::FbxFileWriter(dust3d::Object &object,
|
|||
//std::vector<int32_t> uvIndices;
|
||||
for (decltype(triangleVertexUvs->size()) i = 0; i < triangleVertexUvs->size(); ++i) {
|
||||
for (size_t j = 0; j < 3; ++j) {
|
||||
const auto &uv = (*triangleVertexUvs)[i][j];
|
||||
const auto& uv = (*triangleVertexUvs)[i][j];
|
||||
uvs.push_back((double)uv.x());
|
||||
uvs.push_back((double)1.0 - uv.y());
|
||||
//uvIndices.push_back(uvIndices.size());
|
||||
|
@ -2285,7 +2285,7 @@ FbxFileWriter::FbxFileWriter(dust3d::Object &object,
|
|||
layerElementMaterial.addPropertyNode("Name", "");
|
||||
layerElementMaterial.addPropertyNode("MappingInformationType", "AllSame");
|
||||
layerElementMaterial.addPropertyNode("ReferenceInformationType", "IndexToDirect");
|
||||
std::vector<int32_t> materials = {(int32_t)0};
|
||||
std::vector<int32_t> materials = { (int32_t)0 };
|
||||
layerElementMaterial.addPropertyNode("Materials", materials);
|
||||
layerElementMaterial.addChild(FBXNode());
|
||||
FBXNode layer("Layer");
|
||||
|
@ -2327,7 +2327,7 @@ FbxFileWriter::FbxFileWriter(dust3d::Object &object,
|
|||
int64_t modelId = m_next64Id++;
|
||||
FBXNode model("Model");
|
||||
model.addProperty(modelId);
|
||||
model.addProperty(std::vector<uint8_t>({'u','n','a','m','e','d',0,1,'M','o','d','e','l'}), 'S');
|
||||
model.addProperty(std::vector<uint8_t>({ 'u', 'n', 'a', 'm', 'e', 'd', 0, 1, 'M', 'o', 'd', 'e', 'l' }), 'S');
|
||||
model.addProperty("Mesh");
|
||||
model.addPropertyNode("Version", (int32_t)232);
|
||||
{
|
||||
|
@ -2402,11 +2402,10 @@ FbxFileWriter::FbxFileWriter(dust3d::Object &object,
|
|||
int64_t skinId = 0;
|
||||
int64_t armatureId = 0;
|
||||
|
||||
if (deformerCount > 0)
|
||||
{
|
||||
if (deformerCount > 0) {
|
||||
poseId = m_next64Id++;
|
||||
pose.addProperty(poseId);
|
||||
pose.addProperty(std::vector<uint8_t>({'u','n','a','m','e','d',0,1,'P','o','s','e'}), 'S');
|
||||
pose.addProperty(std::vector<uint8_t>({ 'u', 'n', 'a', 'm', 'e', 'd', 0, 1, 'P', 'o', 's', 'e' }), 'S');
|
||||
pose.addProperty("BindPose");
|
||||
pose.addPropertyNode("Type", "BindPose");
|
||||
pose.addPropertyNode("Version", (int32_t)100);
|
||||
|
@ -2437,7 +2436,7 @@ FbxFileWriter::FbxFileWriter(dust3d::Object &object,
|
|||
FBXNode material("Material");
|
||||
int64_t materialId = m_next64Id++;
|
||||
material.addProperty(materialId);
|
||||
material.addProperty(std::vector<uint8_t>({'M','a','t','e','r','i','a','l',0,1,'S','t','i','n','g','r','a','y','P','B','S'}), 'S');
|
||||
material.addProperty(std::vector<uint8_t>({ 'M', 'a', 't', 'e', 'r', 'i', 'a', 'l', 0, 1, 'S', 't', 'i', 'n', 'g', 'r', 'a', 'y', 'P', 'B', 'S' }), 'S');
|
||||
material.addProperty("");
|
||||
material.addPropertyNode("Version", (int32_t)102);
|
||||
material.addPropertyNode("ShadingModel", "unknown");
|
||||
|
@ -2837,7 +2836,7 @@ FbxFileWriter::FbxFileWriter(dust3d::Object &object,
|
|||
FBXNode implementation("Implementation");
|
||||
int64_t implementationId = m_next64Id++;
|
||||
implementation.addProperty(implementationId);
|
||||
implementation.addProperty(std::vector<uint8_t>({'I','m','p','l','e','m','e','n','t','a','t','i','o','n',0,1,'S','t','i','n','g','r','a','y','P','B','S','_','I','m','p','l','e','m','e','n','t','a','t','i','o','n'}), 'S');
|
||||
implementation.addProperty(std::vector<uint8_t>({ 'I', 'm', 'p', 'l', 'e', 'm', 'e', 'n', 't', 'a', 't', 'i', 'o', 'n', 0, 1, 'S', 't', 'i', 'n', 'g', 'r', 'a', 'y', 'P', 'B', 'S', '_', 'I', 'm', 'p', 'l', 'e', 'm', 'e', 'n', 't', 'a', 't', 'i', 'o', 'n' }), 'S');
|
||||
implementation.addProperty("");
|
||||
implementation.addPropertyNode("Version", (int32_t)100);
|
||||
{
|
||||
|
@ -2900,7 +2899,7 @@ FbxFileWriter::FbxFileWriter(dust3d::Object &object,
|
|||
FBXNode bindingTable("BindingTable");
|
||||
int64_t bindingTableId = m_next64Id++;
|
||||
bindingTable.addProperty(bindingTableId);
|
||||
bindingTable.addProperty(std::vector<uint8_t>({'B','i','n','d','i','n','g','T','a','b','l','e',0,1,'S','t','i','n','g','r','a','y','P','B','S','_','B','i','n','d','i','n','g','T','a','b','l','e'}), 'S');
|
||||
bindingTable.addProperty(std::vector<uint8_t>({ 'B', 'i', 'n', 'd', 'i', 'n', 'g', 'T', 'a', 'b', 'l', 'e', 0, 1, 'S', 't', 'i', 'n', 'g', 'r', 'a', 'y', 'P', 'B', 'S', '_', 'B', 'i', 'n', 'd', 'i', 'n', 'g', 'T', 'a', 'b', 'l', 'e' }), 'S');
|
||||
bindingTable.addProperty("");
|
||||
bindingTable.addPropertyNode("Version", (int32_t)100);
|
||||
{
|
||||
|
@ -3104,7 +3103,7 @@ FbxFileWriter::FbxFileWriter(dust3d::Object &object,
|
|||
}
|
||||
bindingTable.addChild(FBXNode());
|
||||
|
||||
auto addTexture = [&](const QImage *image, const std::vector<uint8_t> &clipName, const std::vector<uint8_t> &textureName, const QString &filename, const QString &propertyName){
|
||||
auto addTexture = [&](const QImage* image, const std::vector<uint8_t>& clipName, const std::vector<uint8_t>& textureName, const QString& filename, const QString& propertyName) {
|
||||
FBXNode video("Video");
|
||||
int64_t videoId = m_next64Id++;
|
||||
video.addProperty(videoId);
|
||||
|
@ -3214,36 +3213,36 @@ FbxFileWriter::FbxFileWriter(dust3d::Object &object,
|
|||
};
|
||||
if (nullptr != textureImage) {
|
||||
addTexture(textureImage,
|
||||
std::vector<uint8_t>({'V','i','d','e','o',0,1,'B','a','s','e','C','o','l','o','r'}),
|
||||
std::vector<uint8_t>({'T','e','x','t','u','r','e',0,1,'B','a','s','e','C','o','l','o','r'}),
|
||||
std::vector<uint8_t>({ 'V', 'i', 'd', 'e', 'o', 0, 1, 'B', 'a', 's', 'e', 'C', 'o', 'l', 'o', 'r' }),
|
||||
std::vector<uint8_t>({ 'T', 'e', 'x', 't', 'u', 'r', 'e', 0, 1, 'B', 'a', 's', 'e', 'C', 'o', 'l', 'o', 'r' }),
|
||||
m_baseName + "_color.png",
|
||||
"Maya|TEX_color_map");
|
||||
}
|
||||
if (nullptr != normalImage) {
|
||||
addTexture(normalImage,
|
||||
std::vector<uint8_t>({'V','i','d','e','o',0,1,'N','o','r','m','a','l'}),
|
||||
std::vector<uint8_t>({'T','e','x','t','u','r','e',0,1,'N','o','r','m','a','l'}),
|
||||
std::vector<uint8_t>({ 'V', 'i', 'd', 'e', 'o', 0, 1, 'N', 'o', 'r', 'm', 'a', 'l' }),
|
||||
std::vector<uint8_t>({ 'T', 'e', 'x', 't', 'u', 'r', 'e', 0, 1, 'N', 'o', 'r', 'm', 'a', 'l' }),
|
||||
m_baseName + "_normal.png",
|
||||
"Maya|TEX_normal_map");
|
||||
}
|
||||
if (nullptr != metalnessImage) {
|
||||
addTexture(metalnessImage,
|
||||
std::vector<uint8_t>({'V','i','d','e','o',0,1,'M','e','t','a','l','l','i','c'}),
|
||||
std::vector<uint8_t>({'T','e','x','t','u','r','e',0,1,'M','e','t','a','l','l','i','c'}),
|
||||
std::vector<uint8_t>({ 'V', 'i', 'd', 'e', 'o', 0, 1, 'M', 'e', 't', 'a', 'l', 'l', 'i', 'c' }),
|
||||
std::vector<uint8_t>({ 'T', 'e', 'x', 't', 'u', 'r', 'e', 0, 1, 'M', 'e', 't', 'a', 'l', 'l', 'i', 'c' }),
|
||||
m_baseName + "_metallic.png",
|
||||
"Maya|TEX_metallic_map");
|
||||
}
|
||||
if (nullptr != roughnessImage) {
|
||||
addTexture(roughnessImage,
|
||||
std::vector<uint8_t>({'V','i','d','e','o',0,1,'R','o','u','g','h','n','e','s','s'}),
|
||||
std::vector<uint8_t>({'T','e','x','t','u','r','e',0,1,'R','o','u','g','h','n','e','s','s'}),
|
||||
std::vector<uint8_t>({ 'V', 'i', 'd', 'e', 'o', 0, 1, 'R', 'o', 'u', 'g', 'h', 'n', 'e', 's', 's' }),
|
||||
std::vector<uint8_t>({ 'T', 'e', 'x', 't', 'u', 'r', 'e', 0, 1, 'R', 'o', 'u', 'g', 'h', 'n', 'e', 's', 's' }),
|
||||
m_baseName + "_roughness.png",
|
||||
"Maya|TEX_roughness_map");
|
||||
}
|
||||
if (nullptr != ambientOcclusionImage) {
|
||||
addTexture(ambientOcclusionImage,
|
||||
std::vector<uint8_t>({'V','i','d','e','o',0,1,'A','o'}),
|
||||
std::vector<uint8_t>({'T','e','x','t','u','r','e',0,1,'A','o'}),
|
||||
std::vector<uint8_t>({ 'V', 'i', 'd', 'e', 'o', 0, 1, 'A', 'o' }),
|
||||
std::vector<uint8_t>({ 'T', 'e', 'x', 't', 'u', 'r', 'e', 0, 1, 'A', 'o' }),
|
||||
m_baseName + "_ao.png",
|
||||
"Maya|TEX_ao_map");
|
||||
}
|
||||
|
@ -3267,7 +3266,7 @@ FbxFileWriter::FbxFileWriter(dust3d::Object &object,
|
|||
FBXNode objects("Objects");
|
||||
objects.addChild(geometry);
|
||||
objects.addChild(model);
|
||||
for (const auto &limbNode: limbNodes) {
|
||||
for (const auto& limbNode : limbNodes) {
|
||||
objects.addChild(limbNode);
|
||||
}
|
||||
if (deformerCount > 0)
|
||||
|
@ -3276,32 +3275,32 @@ FbxFileWriter::FbxFileWriter(dust3d::Object &object,
|
|||
objects.addChild(implementation);
|
||||
objects.addChild(bindingTable);
|
||||
if (textureCount > 0) {
|
||||
for (const auto &texture: textures) {
|
||||
for (const auto& texture : textures) {
|
||||
objects.addChild(texture);
|
||||
}
|
||||
}
|
||||
if (videoCount > 0) {
|
||||
for (const auto &video: videos) {
|
||||
for (const auto& video : videos) {
|
||||
objects.addChild(video);
|
||||
}
|
||||
}
|
||||
for (const auto &deformer: deformers) {
|
||||
for (const auto& deformer : deformers) {
|
||||
objects.addChild(deformer);
|
||||
}
|
||||
for (const auto &nodeAttribute: nodeAttributes) {
|
||||
for (const auto& nodeAttribute : nodeAttributes) {
|
||||
objects.addChild(nodeAttribute);
|
||||
}
|
||||
if (hasAnimation) {
|
||||
for (const auto &animationStack: animationStacks) {
|
||||
for (const auto& animationStack : animationStacks) {
|
||||
objects.addChild(animationStack);
|
||||
}
|
||||
for (const auto &animationLayer: animationLayers) {
|
||||
for (const auto& animationLayer : animationLayers) {
|
||||
objects.addChild(animationLayer);
|
||||
}
|
||||
for (const auto &animationCurveNode: animationCurveNodes) {
|
||||
for (const auto& animationCurveNode : animationCurveNodes) {
|
||||
objects.addChild(animationCurveNode);
|
||||
}
|
||||
for (const auto &animationCurve: animationCurves) {
|
||||
for (const auto& animationCurve : animationCurves) {
|
||||
objects.addChild(animationCurve);
|
||||
}
|
||||
}
|
||||
|
@ -3315,8 +3314,7 @@ FbxFileWriter::FbxFileWriter(dust3d::Object &object,
|
|||
p.addProperty((int64_t)0);
|
||||
connections.addChild(p);
|
||||
}
|
||||
if (armatureId > 0)
|
||||
{
|
||||
if (armatureId > 0) {
|
||||
FBXNode p("C");
|
||||
p.addProperty("OO");
|
||||
p.addProperty(armatureId);
|
||||
|
@ -3330,8 +3328,7 @@ FbxFileWriter::FbxFileWriter(dust3d::Object &object,
|
|||
p.addProperty(modelId);
|
||||
connections.addChild(p);
|
||||
}
|
||||
if (skinId > 0)
|
||||
{
|
||||
if (skinId > 0) {
|
||||
FBXNode p("C");
|
||||
p.addProperty("OO");
|
||||
p.addProperty(skinId);
|
||||
|
@ -3394,11 +3391,11 @@ bool FbxFileWriter::save()
|
|||
return true;
|
||||
}
|
||||
|
||||
std::vector<double> FbxFileWriter::matrixToVector(const QMatrix4x4 &matrix)
|
||||
std::vector<double> FbxFileWriter::matrixToVector(const QMatrix4x4& matrix)
|
||||
{
|
||||
std::vector<double> vec;
|
||||
for (size_t col = 0; col < 4; ++col) {
|
||||
const auto &line = matrix.column(col);
|
||||
const auto& line = matrix.column(col);
|
||||
vec.push_back(line.x());
|
||||
vec.push_back(line.y());
|
||||
vec.push_back(line.z());
|
||||
|
|
|
@ -1,25 +1,24 @@
|
|||
#ifndef DUST3D_APPLICATION_FBX_FILE_H_
|
||||
#define DUST3D_APPLICATION_FBX_FILE_H_
|
||||
|
||||
#include <map>
|
||||
#include <QString>
|
||||
#include "fbxdocument.h"
|
||||
#include <QImage>
|
||||
#include <QMatrix4x4>
|
||||
#include <QQuaternion>
|
||||
#include <QImage>
|
||||
#include <QString>
|
||||
#include <dust3d/base/object.h>
|
||||
#include "fbxdocument.h"
|
||||
#include <map>
|
||||
|
||||
class FbxFileWriter : public QObject
|
||||
{
|
||||
class FbxFileWriter : public QObject {
|
||||
Q_OBJECT
|
||||
public:
|
||||
FbxFileWriter(dust3d::Object &object,
|
||||
const QString &filename,
|
||||
QImage *textureImage=nullptr,
|
||||
QImage *normalImage=nullptr,
|
||||
QImage *metalnessImage=nullptr,
|
||||
QImage *roughnessImage=nullptr,
|
||||
QImage *ambientOcclusionImage=nullptr);
|
||||
FbxFileWriter(dust3d::Object& object,
|
||||
const QString& filename,
|
||||
QImage* textureImage = nullptr,
|
||||
QImage* normalImage = nullptr,
|
||||
QImage* metalnessImage = nullptr,
|
||||
QImage* roughnessImage = nullptr,
|
||||
QImage* ambientOcclusionImage = nullptr);
|
||||
bool save();
|
||||
|
||||
private:
|
||||
|
@ -31,15 +30,15 @@ private:
|
|||
void createDocuments();
|
||||
void createReferences();
|
||||
void createDefinitions(size_t deformerCount,
|
||||
size_t textureCount=0,
|
||||
size_t videoCount=0,
|
||||
bool hasAnimtion=false,
|
||||
size_t animationStackCount=0,
|
||||
size_t animationLayerCount=0,
|
||||
size_t animationCurveNodeCount=0,
|
||||
size_t animationCurveCount=0);
|
||||
size_t textureCount = 0,
|
||||
size_t videoCount = 0,
|
||||
bool hasAnimtion = false,
|
||||
size_t animationStackCount = 0,
|
||||
size_t animationLayerCount = 0,
|
||||
size_t animationCurveNodeCount = 0,
|
||||
size_t animationCurveCount = 0);
|
||||
void createTakes();
|
||||
std::vector<double> matrixToVector(const QMatrix4x4 &matrix);
|
||||
std::vector<double> matrixToVector(const QMatrix4x4& matrix);
|
||||
int64_t secondsToKtime(double seconds);
|
||||
|
||||
int64_t m_next64Id = 612150000;
|
||||
|
@ -51,4 +50,3 @@ private:
|
|||
};
|
||||
|
||||
#endif
|
||||
|
||||
|
|
|
@ -1,11 +1,11 @@
|
|||
#include <QtWidgets>
|
||||
#include "float_number_widget.h"
|
||||
#include "theme.h"
|
||||
#include <QHBoxLayout>
|
||||
#include <QVBoxLayout>
|
||||
#include "theme.h"
|
||||
#include "float_number_widget.h"
|
||||
#include <QtWidgets>
|
||||
|
||||
FloatNumberWidget::FloatNumberWidget(QWidget *parent, bool singleLine) :
|
||||
QWidget(parent)
|
||||
FloatNumberWidget::FloatNumberWidget(QWidget* parent, bool singleLine)
|
||||
: QWidget(parent)
|
||||
{
|
||||
m_slider = new QSlider(Qt::Horizontal, this);
|
||||
m_slider->setRange(0, 100);
|
||||
|
@ -20,7 +20,7 @@ FloatNumberWidget::FloatNumberWidget(QWidget *parent, bool singleLine) :
|
|||
emit valueChanged(fvalue);
|
||||
});
|
||||
|
||||
QBoxLayout *layout = nullptr;
|
||||
QBoxLayout* layout = nullptr;
|
||||
if (singleLine) {
|
||||
layout = new QHBoxLayout(this);
|
||||
layout->setMargin(2);
|
||||
|
@ -48,7 +48,7 @@ void FloatNumberWidget::updateValueLabel(float value)
|
|||
m_label->setText(m_itemName + ": " + valueString);
|
||||
}
|
||||
|
||||
void FloatNumberWidget::setItemName(const QString &name)
|
||||
void FloatNumberWidget::setItemName(const QString& name)
|
||||
{
|
||||
m_itemName = name;
|
||||
updateValueLabel(value());
|
||||
|
|
|
@ -6,14 +6,13 @@
|
|||
QT_FORWARD_DECLARE_CLASS(QLabel)
|
||||
QT_FORWARD_DECLARE_CLASS(QSlider)
|
||||
|
||||
class FloatNumberWidget : public QWidget
|
||||
{
|
||||
class FloatNumberWidget : public QWidget {
|
||||
Q_OBJECT
|
||||
public:
|
||||
explicit FloatNumberWidget(QWidget *parent=nullptr, bool singleLine=true);
|
||||
explicit FloatNumberWidget(QWidget* parent = nullptr, bool singleLine = true);
|
||||
void setRange(float min, float max);
|
||||
float value() const;
|
||||
void setItemName(const QString &name);
|
||||
void setItemName(const QString& name);
|
||||
void setSliderFixedWidth(float width);
|
||||
|
||||
public slots:
|
||||
|
@ -28,8 +27,8 @@ private:
|
|||
void updateValueLabel(float value);
|
||||
|
||||
private:
|
||||
QLabel *m_label = nullptr;
|
||||
QSlider *m_slider = nullptr;
|
||||
QLabel* m_label = nullptr;
|
||||
QSlider* m_slider = nullptr;
|
||||
QString m_itemName;
|
||||
};
|
||||
|
||||
|
|
|
@ -52,26 +52,29 @@
|
|||
|
||||
#include "flow_layout.h"
|
||||
|
||||
FlowLayout::FlowLayout(QWidget *parent, int margin, int hSpacing, int vSpacing)
|
||||
: QLayout(parent), m_hSpace(hSpacing), m_vSpace(vSpacing)
|
||||
FlowLayout::FlowLayout(QWidget* parent, int margin, int hSpacing, int vSpacing)
|
||||
: QLayout(parent)
|
||||
, m_hSpace(hSpacing)
|
||||
, m_vSpace(vSpacing)
|
||||
{
|
||||
setContentsMargins(margin, margin, margin, margin);
|
||||
}
|
||||
|
||||
FlowLayout::FlowLayout(int margin, int hSpacing, int vSpacing)
|
||||
: m_hSpace(hSpacing), m_vSpace(vSpacing)
|
||||
: m_hSpace(hSpacing)
|
||||
, m_vSpace(vSpacing)
|
||||
{
|
||||
setContentsMargins(margin, margin, margin, margin);
|
||||
}
|
||||
|
||||
FlowLayout::~FlowLayout()
|
||||
{
|
||||
QLayoutItem *item;
|
||||
QLayoutItem* item;
|
||||
while ((item = takeAt(0)))
|
||||
delete item;
|
||||
}
|
||||
|
||||
void FlowLayout::addItem(QLayoutItem *item)
|
||||
void FlowLayout::addItem(QLayoutItem* item)
|
||||
{
|
||||
itemList.append(item);
|
||||
}
|
||||
|
@ -99,12 +102,12 @@ int FlowLayout::count() const
|
|||
return itemList.size();
|
||||
}
|
||||
|
||||
QLayoutItem *FlowLayout::itemAt(int index) const
|
||||
QLayoutItem* FlowLayout::itemAt(int index) const
|
||||
{
|
||||
return itemList.value(index);
|
||||
}
|
||||
|
||||
QLayoutItem *FlowLayout::takeAt(int index)
|
||||
QLayoutItem* FlowLayout::takeAt(int index)
|
||||
{
|
||||
if (index >= 0 && index < itemList.size())
|
||||
return itemList.takeAt(index);
|
||||
|
@ -128,7 +131,7 @@ int FlowLayout::heightForWidth(int width) const
|
|||
return height;
|
||||
}
|
||||
|
||||
void FlowLayout::setGeometry(const QRect &rect)
|
||||
void FlowLayout::setGeometry(const QRect& rect)
|
||||
{
|
||||
QLayout::setGeometry(rect);
|
||||
doLayout(rect, false);
|
||||
|
@ -142,15 +145,15 @@ QSize FlowLayout::sizeHint() const
|
|||
QSize FlowLayout::minimumSize() const
|
||||
{
|
||||
QSize size;
|
||||
QLayoutItem *item;
|
||||
QLayoutItem* item;
|
||||
foreach (item, itemList)
|
||||
size = size.expandedTo(item->minimumSize());
|
||||
|
||||
size += QSize(2*margin(), 2*margin());
|
||||
size += QSize(2 * margin(), 2 * margin());
|
||||
return size;
|
||||
}
|
||||
|
||||
int FlowLayout::doLayout(const QRect &rect, bool testOnly) const
|
||||
int FlowLayout::doLayout(const QRect& rect, bool testOnly) const
|
||||
{
|
||||
int left, top, right, bottom;
|
||||
getContentsMargins(&left, &top, &right, &bottom);
|
||||
|
@ -159,9 +162,9 @@ int FlowLayout::doLayout(const QRect &rect, bool testOnly) const
|
|||
int y = effectiveRect.y();
|
||||
int lineHeight = 0;
|
||||
|
||||
QLayoutItem *item;
|
||||
QLayoutItem* item;
|
||||
foreach (item, itemList) {
|
||||
QWidget *wid = item->widget();
|
||||
QWidget* wid = item->widget();
|
||||
int spaceX = horizontalSpacing();
|
||||
if (spaceX == -1)
|
||||
spaceX = wid->style()->layoutSpacing(
|
||||
|
@ -189,13 +192,13 @@ int FlowLayout::doLayout(const QRect &rect, bool testOnly) const
|
|||
|
||||
int FlowLayout::smartSpacing(QStyle::PixelMetric pm) const
|
||||
{
|
||||
QObject *parent = this->parent();
|
||||
QObject* parent = this->parent();
|
||||
if (!parent) {
|
||||
return -1;
|
||||
} else if (parent->isWidgetType()) {
|
||||
QWidget *pw = static_cast<QWidget *>(parent);
|
||||
QWidget* pw = static_cast<QWidget*>(parent);
|
||||
return pw->style()->pixelMetric(pm, 0, pw);
|
||||
} else {
|
||||
return static_cast<QLayout *>(parent)->spacing();
|
||||
return static_cast<QLayout*>(parent)->spacing();
|
||||
}
|
||||
}
|
||||
|
|
|
@ -55,31 +55,30 @@
|
|||
#include <QRect>
|
||||
#include <QStyle>
|
||||
|
||||
class FlowLayout : public QLayout
|
||||
{
|
||||
class FlowLayout : public QLayout {
|
||||
public:
|
||||
explicit FlowLayout(QWidget *parent, int margin=-1, int hSpacing=-1, int vSpacing=-1);
|
||||
explicit FlowLayout(int margin=-1, int hSpacing=-1, int vSpacing=-1);
|
||||
explicit FlowLayout(QWidget* parent, int margin = -1, int hSpacing = -1, int vSpacing = -1);
|
||||
explicit FlowLayout(int margin = -1, int hSpacing = -1, int vSpacing = -1);
|
||||
~FlowLayout();
|
||||
|
||||
void addItem(QLayoutItem *item) override;
|
||||
void addItem(QLayoutItem* item) override;
|
||||
int horizontalSpacing() const;
|
||||
int verticalSpacing() const;
|
||||
Qt::Orientations expandingDirections() const override;
|
||||
bool hasHeightForWidth() const override;
|
||||
int heightForWidth(int) const override;
|
||||
int count() const override;
|
||||
QLayoutItem *itemAt(int index) const override;
|
||||
QLayoutItem* itemAt(int index) const override;
|
||||
QSize minimumSize() const override;
|
||||
void setGeometry(const QRect &rect) override;
|
||||
void setGeometry(const QRect& rect) override;
|
||||
QSize sizeHint() const override;
|
||||
QLayoutItem *takeAt(int index) override;
|
||||
QLayoutItem* takeAt(int index) override;
|
||||
|
||||
private:
|
||||
int doLayout(const QRect &rect, bool testOnly) const;
|
||||
int doLayout(const QRect& rect, bool testOnly) const;
|
||||
int smartSpacing(QStyle::PixelMetric pm) const;
|
||||
|
||||
QList<QLayoutItem *> itemList;
|
||||
QList<QLayoutItem*> itemList;
|
||||
int m_hSpace;
|
||||
int m_vSpace;
|
||||
};
|
||||
|
|
|
@ -1,29 +1,29 @@
|
|||
#include <QFile>
|
||||
#include <QQuaternion>
|
||||
#include "glb_file.h"
|
||||
#include "model_mesh.h"
|
||||
#include "version.h"
|
||||
#include <QByteArray>
|
||||
#include <QDataStream>
|
||||
#include <QFileInfo>
|
||||
#include <QDir>
|
||||
#include <QFile>
|
||||
#include <QFileInfo>
|
||||
#include <QQuaternion>
|
||||
#include <QtCore/qbuffer.h>
|
||||
#include "glb_file.h"
|
||||
#include "version.h"
|
||||
#include "model_mesh.h"
|
||||
|
||||
bool GlbFileWriter::m_enableComment = false;
|
||||
|
||||
GlbFileWriter::GlbFileWriter(dust3d::Object &object,
|
||||
const QString &filename,
|
||||
QImage *textureImage,
|
||||
QImage *normalImage,
|
||||
QImage *ormImage) :
|
||||
m_filename(filename)
|
||||
GlbFileWriter::GlbFileWriter(dust3d::Object& object,
|
||||
const QString& filename,
|
||||
QImage* textureImage,
|
||||
QImage* normalImage,
|
||||
QImage* ormImage)
|
||||
: m_filename(filename)
|
||||
{
|
||||
const std::vector<std::vector<dust3d::Vector3>> *triangleVertexNormals = object.triangleVertexNormals();
|
||||
const std::vector<std::vector<dust3d::Vector3>>* triangleVertexNormals = object.triangleVertexNormals();
|
||||
if (m_outputNormal) {
|
||||
m_outputNormal = nullptr != triangleVertexNormals;
|
||||
}
|
||||
|
||||
const std::vector<std::vector<dust3d::Vector2>> *triangleVertexUvs = object.triangleVertexUvs();
|
||||
const std::vector<std::vector<dust3d::Vector2>>* triangleVertexUvs = object.triangleVertexUvs();
|
||||
if (m_outputUv) {
|
||||
m_outputUv = nullptr != triangleVertexUvs;
|
||||
}
|
||||
|
@ -53,13 +53,13 @@ GlbFileWriter::GlbFileWriter(dust3d::Object &object,
|
|||
|
||||
m_json["asset"]["version"] = "2.0";
|
||||
m_json["asset"]["generator"] = APP_NAME " " APP_HUMAN_VER;
|
||||
m_json["scenes"][0]["nodes"] = {0};
|
||||
m_json["scenes"][0]["nodes"] = { 0 };
|
||||
|
||||
m_json["nodes"][0]["mesh"] = 0;
|
||||
|
||||
std::vector<dust3d::Vector3> triangleVertexPositions;
|
||||
std::vector<size_t> triangleVertexOldIndices;
|
||||
for (const auto &triangleIndices: object.triangles) {
|
||||
for (const auto& triangleIndices : object.triangles) {
|
||||
for (size_t j = 0; j < 3; ++j) {
|
||||
triangleVertexOldIndices.push_back(triangleIndices[j]);
|
||||
triangleVertexPositions.push_back(object.vertices[triangleIndices[j]]);
|
||||
|
@ -124,7 +124,7 @@ GlbFileWriter::GlbFileWriter(dust3d::Object &object,
|
|||
float maxY = -100;
|
||||
float minZ = 100;
|
||||
float maxZ = -100;
|
||||
for (const auto &position: triangleVertexPositions) {
|
||||
for (const auto& position : triangleVertexPositions) {
|
||||
if (position.x() < minX)
|
||||
minX = position.x();
|
||||
if (position.x() > maxX)
|
||||
|
@ -140,7 +140,7 @@ GlbFileWriter::GlbFileWriter(dust3d::Object &object,
|
|||
binStream << (float)position.x() << (float)position.y() << (float)position.z();
|
||||
}
|
||||
Q_ASSERT((int)triangleVertexPositions.size() * 3 * sizeof(float) == m_binByteArray.size() - bufferViewFromOffset);
|
||||
m_json["bufferViews"][bufferViewIndex]["byteLength"] = triangleVertexPositions.size() * 3 * sizeof(float);
|
||||
m_json["bufferViews"][bufferViewIndex]["byteLength"] = triangleVertexPositions.size() * 3 * sizeof(float);
|
||||
m_json["bufferViews"][bufferViewIndex]["target"] = 34962;
|
||||
alignBin();
|
||||
if (m_enableComment)
|
||||
|
@ -148,10 +148,10 @@ GlbFileWriter::GlbFileWriter(dust3d::Object &object,
|
|||
m_json["accessors"][bufferViewIndex]["bufferView"] = bufferViewIndex;
|
||||
m_json["accessors"][bufferViewIndex]["byteOffset"] = 0;
|
||||
m_json["accessors"][bufferViewIndex]["componentType"] = 5126;
|
||||
m_json["accessors"][bufferViewIndex]["count"] = triangleVertexPositions.size();
|
||||
m_json["accessors"][bufferViewIndex]["count"] = triangleVertexPositions.size();
|
||||
m_json["accessors"][bufferViewIndex]["type"] = "VEC3";
|
||||
m_json["accessors"][bufferViewIndex]["max"] = {maxX, maxY, maxZ};
|
||||
m_json["accessors"][bufferViewIndex]["min"] = {minX, minY, minZ};
|
||||
m_json["accessors"][bufferViewIndex]["max"] = { maxX, maxY, maxZ };
|
||||
m_json["accessors"][bufferViewIndex]["min"] = { minX, minY, minZ };
|
||||
bufferViewIndex++;
|
||||
|
||||
if (m_outputNormal) {
|
||||
|
@ -159,15 +159,15 @@ GlbFileWriter::GlbFileWriter(dust3d::Object &object,
|
|||
m_json["bufferViews"][bufferViewIndex]["buffer"] = 0;
|
||||
m_json["bufferViews"][bufferViewIndex]["byteOffset"] = bufferViewFromOffset;
|
||||
QStringList normalList;
|
||||
for (const auto &normals: (*triangleVertexNormals)) {
|
||||
for (const auto &it: normals) {
|
||||
for (const auto& normals : (*triangleVertexNormals)) {
|
||||
for (const auto& it : normals) {
|
||||
binStream << (float)it.x() << (float)it.y() << (float)it.z();
|
||||
if (m_enableComment && m_outputNormal)
|
||||
normalList.append(QString("<%1,%2,%3>").arg(QString::number(it.x())).arg(QString::number(it.y())).arg(QString::number(it.z())));
|
||||
}
|
||||
}
|
||||
Q_ASSERT((int)triangleVertexNormals->size() * 3 * 3 * sizeof(float) == m_binByteArray.size() - bufferViewFromOffset);
|
||||
m_json["bufferViews"][bufferViewIndex]["byteLength"] = triangleVertexNormals->size() * 3 * 3 * sizeof(float);
|
||||
m_json["bufferViews"][bufferViewIndex]["byteLength"] = triangleVertexNormals->size() * 3 * 3 * sizeof(float);
|
||||
m_json["bufferViews"][bufferViewIndex]["target"] = 34962;
|
||||
alignBin();
|
||||
if (m_enableComment)
|
||||
|
@ -175,7 +175,7 @@ GlbFileWriter::GlbFileWriter(dust3d::Object &object,
|
|||
m_json["accessors"][bufferViewIndex]["bufferView"] = bufferViewIndex;
|
||||
m_json["accessors"][bufferViewIndex]["byteOffset"] = 0;
|
||||
m_json["accessors"][bufferViewIndex]["componentType"] = 5126;
|
||||
m_json["accessors"][bufferViewIndex]["count"] = triangleVertexNormals->size() * 3;
|
||||
m_json["accessors"][bufferViewIndex]["count"] = triangleVertexNormals->size() * 3;
|
||||
m_json["accessors"][bufferViewIndex]["type"] = "VEC3";
|
||||
bufferViewIndex++;
|
||||
}
|
||||
|
@ -184,8 +184,8 @@ GlbFileWriter::GlbFileWriter(dust3d::Object &object,
|
|||
bufferViewFromOffset = (int)m_binByteArray.size();
|
||||
m_json["bufferViews"][bufferViewIndex]["buffer"] = 0;
|
||||
m_json["bufferViews"][bufferViewIndex]["byteOffset"] = bufferViewFromOffset;
|
||||
for (const auto &uvs: (*triangleVertexUvs)) {
|
||||
for (const auto &it: uvs)
|
||||
for (const auto& uvs : (*triangleVertexUvs)) {
|
||||
for (const auto& it : uvs)
|
||||
binStream << (float)it.x() << (float)it.y();
|
||||
}
|
||||
m_json["bufferViews"][bufferViewIndex]["byteLength"] = m_binByteArray.size() - bufferViewFromOffset;
|
||||
|
@ -195,7 +195,7 @@ GlbFileWriter::GlbFileWriter(dust3d::Object &object,
|
|||
m_json["accessors"][bufferViewIndex]["bufferView"] = bufferViewIndex;
|
||||
m_json["accessors"][bufferViewIndex]["byteOffset"] = 0;
|
||||
m_json["accessors"][bufferViewIndex]["componentType"] = 5126;
|
||||
m_json["accessors"][bufferViewIndex]["count"] = triangleVertexUvs->size() * 3;
|
||||
m_json["accessors"][bufferViewIndex]["count"] = triangleVertexUvs->size() * 3;
|
||||
m_json["accessors"][bufferViewIndex]["type"] = "VEC2";
|
||||
bufferViewIndex++;
|
||||
}
|
||||
|
@ -291,9 +291,7 @@ bool GlbFileWriter::save()
|
|||
uint32_t headerSize = 12;
|
||||
uint32_t chunk0DescriptionSize = 8;
|
||||
uint32_t chunk1DescriptionSize = 8;
|
||||
uint32_t fileSize = headerSize +
|
||||
chunk0DescriptionSize + m_jsonByteArray.size() +
|
||||
chunk1DescriptionSize + m_binByteArray.size();
|
||||
uint32_t fileSize = headerSize + chunk0DescriptionSize + m_jsonByteArray.size() + chunk1DescriptionSize + m_binByteArray.size();
|
||||
|
||||
qDebug() << "Chunk 0 data size:" << m_jsonByteArray.size();
|
||||
qDebug() << "Chunk 1 data size:" << m_binByteArray.size();
|
||||
|
|
|
@ -1,35 +1,37 @@
|
|||
#ifndef DUST3D_APPLICATION_GLB_FILE_H_
|
||||
#define DUST3D_APPLICATION_GLB_FILE_H_
|
||||
|
||||
#include <QObject>
|
||||
#include <QString>
|
||||
#include <QByteArray>
|
||||
#include <QMatrix4x4>
|
||||
#include <vector>
|
||||
#include <QQuaternion>
|
||||
#include <QImage>
|
||||
#include <dust3d/base/object.h>
|
||||
#include "json.hpp"
|
||||
#include "document.h"
|
||||
#include "json.hpp"
|
||||
#include <QByteArray>
|
||||
#include <QImage>
|
||||
#include <QMatrix4x4>
|
||||
#include <QObject>
|
||||
#include <QQuaternion>
|
||||
#include <QString>
|
||||
#include <dust3d/base/object.h>
|
||||
#include <vector>
|
||||
|
||||
class GlbFileWriter : public QObject
|
||||
{
|
||||
class GlbFileWriter : public QObject {
|
||||
Q_OBJECT
|
||||
public:
|
||||
GlbFileWriter(dust3d::Object &object,
|
||||
const QString &filename,
|
||||
QImage *textureImage=nullptr,
|
||||
QImage *normalImage=nullptr,
|
||||
QImage *ormImage=nullptr);
|
||||
GlbFileWriter(dust3d::Object& object,
|
||||
const QString& filename,
|
||||
QImage* textureImage = nullptr,
|
||||
QImage* normalImage = nullptr,
|
||||
QImage* ormImage = nullptr);
|
||||
bool save();
|
||||
|
||||
private:
|
||||
QString m_filename;
|
||||
bool m_outputNormal = true;
|
||||
bool m_outputUv = true;
|
||||
QByteArray m_binByteArray;
|
||||
QByteArray m_jsonByteArray;
|
||||
|
||||
private:
|
||||
nlohmann::json m_json;
|
||||
|
||||
public:
|
||||
static bool m_enableComment;
|
||||
};
|
||||
|
|
|
@ -5,31 +5,31 @@ GraphicsContainerWidget::GraphicsContainerWidget()
|
|||
setMouseTracking(true);
|
||||
}
|
||||
|
||||
void GraphicsContainerWidget::resizeEvent(QResizeEvent *event)
|
||||
void GraphicsContainerWidget::resizeEvent(QResizeEvent* event)
|
||||
{
|
||||
if (m_graphicsWidget && m_graphicsWidget->size() != event->size())
|
||||
emit containerSizeChanged(event->size());
|
||||
}
|
||||
|
||||
void GraphicsContainerWidget::mousePressEvent(QMouseEvent *event)
|
||||
void GraphicsContainerWidget::mousePressEvent(QMouseEvent* event)
|
||||
{
|
||||
if (m_modelWidget)
|
||||
m_modelWidget->inputMousePressEventFromOtherWidget(event);
|
||||
}
|
||||
|
||||
void GraphicsContainerWidget::mouseMoveEvent(QMouseEvent *event)
|
||||
void GraphicsContainerWidget::mouseMoveEvent(QMouseEvent* event)
|
||||
{
|
||||
if (m_modelWidget)
|
||||
m_modelWidget->inputMouseMoveEventFromOtherWidget(event);
|
||||
}
|
||||
|
||||
void GraphicsContainerWidget::mouseReleaseEvent(QMouseEvent *event)
|
||||
void GraphicsContainerWidget::mouseReleaseEvent(QMouseEvent* event)
|
||||
{
|
||||
if (m_modelWidget)
|
||||
m_modelWidget->inputMouseReleaseEventFromOtherWidget(event);
|
||||
}
|
||||
|
||||
void GraphicsContainerWidget::wheelEvent(QWheelEvent *event)
|
||||
void GraphicsContainerWidget::wheelEvent(QWheelEvent* event)
|
||||
{
|
||||
if (m_graphicsWidget) {
|
||||
m_graphicsWidget->inputWheelEventFromOtherWidget(event);
|
||||
|
@ -40,12 +40,12 @@ void GraphicsContainerWidget::wheelEvent(QWheelEvent *event)
|
|||
m_modelWidget->inputWheelEventFromOtherWidget(event);
|
||||
}
|
||||
|
||||
void GraphicsContainerWidget::setGraphicsWidget(SkeletonGraphicsWidget *graphicsWidget)
|
||||
void GraphicsContainerWidget::setGraphicsWidget(SkeletonGraphicsWidget* graphicsWidget)
|
||||
{
|
||||
m_graphicsWidget = graphicsWidget;
|
||||
}
|
||||
|
||||
void GraphicsContainerWidget::setModelWidget(ModelWidget *modelWidget)
|
||||
void GraphicsContainerWidget::setModelWidget(ModelWidget* modelWidget)
|
||||
{
|
||||
m_modelWidget = modelWidget;
|
||||
}
|
||||
|
|
|
@ -1,31 +1,33 @@
|
|||
#ifndef DUST3D_APPLICATION_GRAPHICS_CONTAINER_WIDGET_H_
|
||||
#define DUST3D_APPLICATION_GRAPHICS_CONTAINER_WIDGET_H_
|
||||
|
||||
#include <QWidget>
|
||||
#include <QResizeEvent>
|
||||
#include <QMouseEvent>
|
||||
#include <QWheelEvent>
|
||||
#include "model_widget.h"
|
||||
#include "skeleton_graphics_widget.h"
|
||||
#include <QMouseEvent>
|
||||
#include <QResizeEvent>
|
||||
#include <QWheelEvent>
|
||||
#include <QWidget>
|
||||
|
||||
class GraphicsContainerWidget : public QWidget
|
||||
{
|
||||
class GraphicsContainerWidget : public QWidget {
|
||||
Q_OBJECT
|
||||
signals:
|
||||
void containerSizeChanged(QSize size);
|
||||
|
||||
public:
|
||||
GraphicsContainerWidget();
|
||||
void setGraphicsWidget(SkeletonGraphicsWidget *graphicsWidget);
|
||||
void setModelWidget(ModelWidget *modelWidget);
|
||||
void setGraphicsWidget(SkeletonGraphicsWidget* graphicsWidget);
|
||||
void setModelWidget(ModelWidget* modelWidget);
|
||||
|
||||
protected:
|
||||
void resizeEvent(QResizeEvent *event) override;
|
||||
void mousePressEvent(QMouseEvent *event) override;
|
||||
void mouseMoveEvent(QMouseEvent *event) override;
|
||||
void mouseReleaseEvent(QMouseEvent *event) override;
|
||||
void wheelEvent(QWheelEvent *event) override;
|
||||
void resizeEvent(QResizeEvent* event) override;
|
||||
void mousePressEvent(QMouseEvent* event) override;
|
||||
void mouseMoveEvent(QMouseEvent* event) override;
|
||||
void mouseReleaseEvent(QMouseEvent* event) override;
|
||||
void wheelEvent(QWheelEvent* event) override;
|
||||
|
||||
private:
|
||||
ModelWidget *m_modelWidget = nullptr;
|
||||
SkeletonGraphicsWidget *m_graphicsWidget = nullptr;
|
||||
ModelWidget* m_modelWidget = nullptr;
|
||||
SkeletonGraphicsWidget* m_graphicsWidget = nullptr;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
#include "horizontal_line_widget.h"
|
||||
|
||||
HorizontalLineWidget::HorizontalLineWidget() :
|
||||
QWidget()
|
||||
HorizontalLineWidget::HorizontalLineWidget()
|
||||
: QWidget()
|
||||
{
|
||||
setFixedHeight(1);
|
||||
setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Fixed);
|
||||
|
|
|
@ -3,8 +3,7 @@
|
|||
|
||||
#include <QWidget>
|
||||
|
||||
class HorizontalLineWidget : public QWidget
|
||||
{
|
||||
class HorizontalLineWidget : public QWidget {
|
||||
Q_OBJECT
|
||||
public:
|
||||
HorizontalLineWidget();
|
||||
|
|
|
@ -1,19 +1,18 @@
|
|||
#include <map>
|
||||
#include "image_forever.h"
|
||||
#include <QMutex>
|
||||
#include <QMutexLocker>
|
||||
#include <QtCore/qbuffer.h>
|
||||
#include "image_forever.h"
|
||||
#include <map>
|
||||
|
||||
struct ImageForeverItem
|
||||
{
|
||||
QImage *image;
|
||||
struct ImageForeverItem {
|
||||
QImage* image;
|
||||
dust3d::Uuid id;
|
||||
QByteArray *imageByteArray;
|
||||
QByteArray* imageByteArray;
|
||||
};
|
||||
static std::map<dust3d::Uuid, ImageForeverItem> g_foreverMap;
|
||||
static QMutex g_mapMutex;
|
||||
|
||||
const QImage *ImageForever::get(const dust3d::Uuid &id)
|
||||
const QImage* ImageForever::get(const dust3d::Uuid& id)
|
||||
{
|
||||
QMutexLocker locker(&g_mapMutex);
|
||||
auto findResult = g_foreverMap.find(id);
|
||||
|
@ -22,7 +21,7 @@ const QImage *ImageForever::get(const dust3d::Uuid &id)
|
|||
return findResult->second.image;
|
||||
}
|
||||
|
||||
void ImageForever::copy(const dust3d::Uuid &id, QImage &image)
|
||||
void ImageForever::copy(const dust3d::Uuid& id, QImage& image)
|
||||
{
|
||||
QMutexLocker locker(&g_mapMutex);
|
||||
auto findResult = g_foreverMap.find(id);
|
||||
|
@ -31,7 +30,7 @@ void ImageForever::copy(const dust3d::Uuid &id, QImage &image)
|
|||
image = *findResult->second.image;
|
||||
}
|
||||
|
||||
const QByteArray *ImageForever::getPngByteArray(const dust3d::Uuid &id)
|
||||
const QByteArray* ImageForever::getPngByteArray(const dust3d::Uuid& id)
|
||||
{
|
||||
QMutexLocker locker(&g_mapMutex);
|
||||
auto findResult = g_foreverMap.find(id);
|
||||
|
@ -40,7 +39,7 @@ const QByteArray *ImageForever::getPngByteArray(const dust3d::Uuid &id)
|
|||
return findResult->second.imageByteArray;
|
||||
}
|
||||
|
||||
dust3d::Uuid ImageForever::add(const QImage *image, dust3d::Uuid toId)
|
||||
dust3d::Uuid ImageForever::add(const QImage* image, dust3d::Uuid toId)
|
||||
{
|
||||
QMutexLocker locker(&g_mapMutex);
|
||||
if (nullptr == image)
|
||||
|
@ -48,16 +47,16 @@ dust3d::Uuid ImageForever::add(const QImage *image, dust3d::Uuid toId)
|
|||
dust3d::Uuid newId = toId.isNull() ? dust3d::Uuid::createUuid() : toId;
|
||||
if (g_foreverMap.find(newId) != g_foreverMap.end())
|
||||
return newId;
|
||||
QImage *newImage = new QImage(*image);
|
||||
QByteArray *imageByteArray = new QByteArray();
|
||||
QImage* newImage = new QImage(*image);
|
||||
QByteArray* imageByteArray = new QByteArray();
|
||||
QBuffer pngBuffer(imageByteArray);
|
||||
pngBuffer.open(QIODevice::WriteOnly);
|
||||
newImage->save(&pngBuffer, "PNG");
|
||||
g_foreverMap[newId] = {newImage, newId, imageByteArray};
|
||||
g_foreverMap[newId] = { newImage, newId, imageByteArray };
|
||||
return newId;
|
||||
}
|
||||
|
||||
void ImageForever::remove(const dust3d::Uuid &id)
|
||||
void ImageForever::remove(const dust3d::Uuid& id)
|
||||
{
|
||||
QMutexLocker locker(&g_mapMutex);
|
||||
auto findImage = g_foreverMap.find(id);
|
||||
|
|
|
@ -1,18 +1,17 @@
|
|||
#ifndef DUST3D_APPLICATION_IMAGE_FOREVER_H_
|
||||
#define DUST3D_APPLICATION_IMAGE_FOREVER_H_
|
||||
|
||||
#include <QImage>
|
||||
#include <QByteArray>
|
||||
#include <QImage>
|
||||
#include <dust3d/base/uuid.h>
|
||||
|
||||
class ImageForever
|
||||
{
|
||||
class ImageForever {
|
||||
public:
|
||||
static const QImage *get(const dust3d::Uuid &id);
|
||||
static void copy(const dust3d::Uuid &id, QImage &image);
|
||||
static const QByteArray *getPngByteArray(const dust3d::Uuid &id);
|
||||
static dust3d::Uuid add(const QImage *image, dust3d::Uuid toId=dust3d::Uuid());
|
||||
static void remove(const dust3d::Uuid &id);
|
||||
static const QImage* get(const dust3d::Uuid& id);
|
||||
static void copy(const dust3d::Uuid& id, QImage& image);
|
||||
static const QByteArray* getPngByteArray(const dust3d::Uuid& id);
|
||||
static dust3d::Uuid add(const QImage* image, dust3d::Uuid toId = dust3d::Uuid());
|
||||
static void remove(const dust3d::Uuid& id);
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
@ -1,28 +1,28 @@
|
|||
#include <QPainter>
|
||||
#include "image_preview_widget.h"
|
||||
#include <QPainter>
|
||||
|
||||
ImagePreviewWidget::ImagePreviewWidget(QWidget *parent) :
|
||||
QWidget(parent)
|
||||
ImagePreviewWidget::ImagePreviewWidget(QWidget* parent)
|
||||
: QWidget(parent)
|
||||
{
|
||||
}
|
||||
|
||||
void ImagePreviewWidget::updateImage(const QImage &image)
|
||||
void ImagePreviewWidget::updateImage(const QImage& image)
|
||||
{
|
||||
m_image = image;
|
||||
update();
|
||||
}
|
||||
|
||||
void ImagePreviewWidget::updateBackgroundColor(const QColor &color)
|
||||
void ImagePreviewWidget::updateBackgroundColor(const QColor& color)
|
||||
{
|
||||
m_backgroundColor = color;
|
||||
}
|
||||
|
||||
void ImagePreviewWidget::mousePressEvent(QMouseEvent *event)
|
||||
void ImagePreviewWidget::mousePressEvent(QMouseEvent* event)
|
||||
{
|
||||
emit clicked();
|
||||
}
|
||||
|
||||
void ImagePreviewWidget::paintEvent(QPaintEvent *event)
|
||||
void ImagePreviewWidget::paintEvent(QPaintEvent* event)
|
||||
{
|
||||
QPainter painter(this);
|
||||
if (!m_image.isNull())
|
||||
|
@ -30,4 +30,3 @@ void ImagePreviewWidget::paintEvent(QPaintEvent *event)
|
|||
else
|
||||
painter.fillRect(QRect(0, 0, width(), height()), QBrush(m_backgroundColor));
|
||||
}
|
||||
|
||||
|
|
|
@ -1,30 +1,30 @@
|
|||
#ifndef DUST3D_APPLICATION_IMAGE_PREVIEW_WIDGET_H_
|
||||
#define DUST3D_APPLICATION_IMAGE_PREVIEW_WIDGET_H_
|
||||
|
||||
#include <QWidget>
|
||||
#include <QImage>
|
||||
#include <QPaintEvent>
|
||||
#include <QMouseEvent>
|
||||
#include <QPaintEvent>
|
||||
#include <QWidget>
|
||||
|
||||
class ImagePreviewWidget : public QWidget
|
||||
{
|
||||
class ImagePreviewWidget : public QWidget {
|
||||
Q_OBJECT
|
||||
signals:
|
||||
void clicked();
|
||||
|
||||
public:
|
||||
ImagePreviewWidget(QWidget *parent=nullptr);
|
||||
void updateImage(const QImage &image);
|
||||
void updateBackgroundColor(const QColor &color);
|
||||
ImagePreviewWidget(QWidget* parent = nullptr);
|
||||
void updateImage(const QImage& image);
|
||||
void updateBackgroundColor(const QColor& color);
|
||||
|
||||
protected:
|
||||
void paintEvent(QPaintEvent *event);
|
||||
void mousePressEvent(QMouseEvent *event);
|
||||
void paintEvent(QPaintEvent* event);
|
||||
void mousePressEvent(QMouseEvent* event);
|
||||
|
||||
private:
|
||||
QImage m_image;
|
||||
QColor m_backgroundColor;
|
||||
|
||||
void resizeImage(QImage *image, const QSize &newSize);
|
||||
void resizeImage(QImage* image, const QSize& newSize);
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
@ -1,9 +1,9 @@
|
|||
#include <QHBoxLayout>
|
||||
#include "info_label.h"
|
||||
#include "theme.h"
|
||||
#include <QHBoxLayout>
|
||||
|
||||
InfoLabel::InfoLabel(const QString &text, QWidget *parent) :
|
||||
QWidget(parent)
|
||||
InfoLabel::InfoLabel(const QString& text, QWidget* parent)
|
||||
: QWidget(parent)
|
||||
{
|
||||
m_icon = new QLabel(QChar(fa::infocircle));
|
||||
Theme::initAwesomeLabel(m_icon);
|
||||
|
@ -11,7 +11,7 @@ InfoLabel::InfoLabel(const QString &text, QWidget *parent) :
|
|||
m_label = new QLabel(text);
|
||||
m_label->setWordWrap(true);
|
||||
|
||||
QHBoxLayout *mainLayout = new QHBoxLayout;
|
||||
QHBoxLayout* mainLayout = new QHBoxLayout;
|
||||
mainLayout->addWidget(m_icon);
|
||||
mainLayout->addWidget(m_label);
|
||||
mainLayout->addStretch();
|
||||
|
@ -19,7 +19,7 @@ InfoLabel::InfoLabel(const QString &text, QWidget *parent) :
|
|||
setLayout(mainLayout);
|
||||
}
|
||||
|
||||
void InfoLabel::setText(const QString &text)
|
||||
void InfoLabel::setText(const QString& text)
|
||||
{
|
||||
m_label->setText(text);
|
||||
}
|
||||
|
|
|
@ -1,18 +1,18 @@
|
|||
#ifndef DUST3D_APPLICATION_INFO_LABEL_H_
|
||||
#define DUST3D_APPLICATION_INFO_LABEL_H_
|
||||
|
||||
#include <QLabel>
|
||||
#include <QIcon>
|
||||
#include <QLabel>
|
||||
#include <QWidget>
|
||||
|
||||
class InfoLabel : public QWidget
|
||||
{
|
||||
class InfoLabel : public QWidget {
|
||||
public:
|
||||
InfoLabel(const QString &text=QString(), QWidget *parent=nullptr);
|
||||
void setText(const QString &text);
|
||||
InfoLabel(const QString& text = QString(), QWidget* parent = nullptr);
|
||||
void setText(const QString& text);
|
||||
|
||||
private:
|
||||
QLabel *m_label = nullptr;
|
||||
QLabel *m_icon = nullptr;
|
||||
QLabel* m_label = nullptr;
|
||||
QLabel* m_icon = nullptr;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
@ -1,11 +1,11 @@
|
|||
#include <QtWidgets>
|
||||
#include "int_number_widget.h"
|
||||
#include "theme.h"
|
||||
#include <QHBoxLayout>
|
||||
#include <QVBoxLayout>
|
||||
#include "theme.h"
|
||||
#include "int_number_widget.h"
|
||||
#include <QtWidgets>
|
||||
|
||||
IntNumberWidget::IntNumberWidget(QWidget *parent, bool singleLine) :
|
||||
QWidget(parent)
|
||||
IntNumberWidget::IntNumberWidget(QWidget* parent, bool singleLine)
|
||||
: QWidget(parent)
|
||||
{
|
||||
m_slider = new QSlider(Qt::Horizontal, this);
|
||||
m_slider->setRange(0, 100);
|
||||
|
@ -19,7 +19,7 @@ IntNumberWidget::IntNumberWidget(QWidget *parent, bool singleLine) :
|
|||
emit valueChanged(value);
|
||||
});
|
||||
|
||||
QBoxLayout *layout = nullptr;
|
||||
QBoxLayout* layout = nullptr;
|
||||
if (singleLine) {
|
||||
layout = new QHBoxLayout(this);
|
||||
layout->setMargin(2);
|
||||
|
@ -42,7 +42,7 @@ void IntNumberWidget::updateValueLabel(int value)
|
|||
m_label->setText(m_itemName + ": " + valueString);
|
||||
}
|
||||
|
||||
void IntNumberWidget::setItemName(const QString &name)
|
||||
void IntNumberWidget::setItemName(const QString& name)
|
||||
{
|
||||
m_itemName = name;
|
||||
updateValueLabel(value());
|
||||
|
|
|
@ -6,14 +6,13 @@
|
|||
QT_FORWARD_DECLARE_CLASS(QLabel)
|
||||
QT_FORWARD_DECLARE_CLASS(QSlider)
|
||||
|
||||
class IntNumberWidget : public QWidget
|
||||
{
|
||||
class IntNumberWidget : public QWidget {
|
||||
Q_OBJECT
|
||||
public:
|
||||
explicit IntNumberWidget(QWidget *parent = nullptr, bool singleLine=true);
|
||||
explicit IntNumberWidget(QWidget* parent = nullptr, bool singleLine = true);
|
||||
void setRange(int min, int max);
|
||||
int value() const;
|
||||
void setItemName(const QString &name);
|
||||
void setItemName(const QString& name);
|
||||
|
||||
public slots:
|
||||
void increaseValue();
|
||||
|
@ -27,8 +26,8 @@ private:
|
|||
void updateValueLabel(int value);
|
||||
|
||||
private:
|
||||
QLabel *m_label = nullptr;
|
||||
QSlider *m_slider = nullptr;
|
||||
QLabel* m_label = nullptr;
|
||||
QSlider* m_slider = nullptr;
|
||||
QString m_itemName;
|
||||
};
|
||||
|
||||
|
|
|
@ -1,12 +1,12 @@
|
|||
#include <QMetaType>
|
||||
#include <QDir>
|
||||
#include "log_browser.h"
|
||||
#include "log_browser_dialog.h"
|
||||
#include <QDir>
|
||||
#include <QMetaType>
|
||||
|
||||
bool LogBrowser::m_enableOutputToFile = true;
|
||||
|
||||
LogBrowser::LogBrowser(QObject *parent) :
|
||||
QObject(parent)
|
||||
LogBrowser::LogBrowser(QObject* parent)
|
||||
: QObject(parent)
|
||||
{
|
||||
qRegisterMetaType<QtMsgType>("QtMsgType");
|
||||
m_browserDialog = new LogBrowserDialog;
|
||||
|
@ -42,7 +42,7 @@ bool LogBrowser::isDialogVisible()
|
|||
return m_browserDialog->isVisible();
|
||||
}
|
||||
|
||||
void LogBrowser::outputMessage(QtMsgType type, const QString &msg, const QString &source, int line)
|
||||
void LogBrowser::outputMessage(QtMsgType type, const QString& msg, const QString& source, int line)
|
||||
{
|
||||
if (m_outputTo) {
|
||||
fprintf(m_outputTo, "[%s:%d]: %s\n", source.toUtf8().constData(), line, msg.toUtf8().constData());
|
||||
|
|
|
@ -6,25 +6,24 @@
|
|||
|
||||
class LogBrowserDialog;
|
||||
|
||||
class LogBrowser : public QObject
|
||||
{
|
||||
class LogBrowser : public QObject {
|
||||
Q_OBJECT
|
||||
public:
|
||||
explicit LogBrowser(QObject *parent=0);
|
||||
explicit LogBrowser(QObject* parent = 0);
|
||||
~LogBrowser();
|
||||
|
||||
public slots:
|
||||
void outputMessage(QtMsgType type, const QString &msg, const QString &source, int line);
|
||||
void outputMessage(QtMsgType type, const QString& msg, const QString& source, int line);
|
||||
void showDialog();
|
||||
void hideDialog();
|
||||
bool isDialogVisible();
|
||||
|
||||
signals:
|
||||
void sendMessage(QtMsgType type, const QString &msg, const QString &source, int line);
|
||||
void sendMessage(QtMsgType type, const QString& msg, const QString& source, int line);
|
||||
|
||||
private:
|
||||
LogBrowserDialog *m_browserDialog = nullptr;
|
||||
FILE *m_outputTo = nullptr;
|
||||
LogBrowserDialog* m_browserDialog = nullptr;
|
||||
FILE* m_outputTo = nullptr;
|
||||
static bool m_enableOutputToFile;
|
||||
};
|
||||
|
||||
|
|
|
@ -1,30 +1,30 @@
|
|||
#include <QVBoxLayout>
|
||||
#include <QHBoxLayout>
|
||||
#include <QTextBrowser>
|
||||
#include <QPushButton>
|
||||
#include <QFileDialog>
|
||||
#include <QDir>
|
||||
#include <QFile>
|
||||
#include <QMessageBox>
|
||||
#include <QTextStream>
|
||||
#include <QCloseEvent>
|
||||
#include <QKeyEvent>
|
||||
#include "version.h"
|
||||
#include "log_browser_dialog.h"
|
||||
#include "document_window.h"
|
||||
#include "version.h"
|
||||
#include <QCloseEvent>
|
||||
#include <QDir>
|
||||
#include <QFile>
|
||||
#include <QFileDialog>
|
||||
#include <QHBoxLayout>
|
||||
#include <QKeyEvent>
|
||||
#include <QMessageBox>
|
||||
#include <QPushButton>
|
||||
#include <QTextBrowser>
|
||||
#include <QTextStream>
|
||||
#include <QVBoxLayout>
|
||||
|
||||
LogBrowserDialog::LogBrowserDialog(QWidget *parent) :
|
||||
QDialog(parent)
|
||||
LogBrowserDialog::LogBrowserDialog(QWidget* parent)
|
||||
: QDialog(parent)
|
||||
{
|
||||
setWindowFlags(windowFlags() | Qt::WindowStaysOnTopHint);
|
||||
|
||||
QVBoxLayout *layout = new QVBoxLayout;
|
||||
QVBoxLayout* layout = new QVBoxLayout;
|
||||
setLayout(layout);
|
||||
|
||||
m_browser = new QTextBrowser(this);
|
||||
layout->addWidget(m_browser);
|
||||
|
||||
QHBoxLayout *buttonLayout = new QHBoxLayout;
|
||||
QHBoxLayout* buttonLayout = new QHBoxLayout;
|
||||
buttonLayout->setContentsMargins(0, 0, 0, 0);
|
||||
layout->addLayout(buttonLayout);
|
||||
|
||||
|
@ -47,14 +47,11 @@ LogBrowserDialog::LogBrowserDialog(QWidget *parent) :
|
|||
hide();
|
||||
}
|
||||
|
||||
|
||||
LogBrowserDialog::~LogBrowserDialog()
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
|
||||
void LogBrowserDialog::outputMessage(QtMsgType type, const QString &msg, const QString &source, int line)
|
||||
void LogBrowserDialog::outputMessage(QtMsgType type, const QString& msg, const QString& source, int line)
|
||||
{
|
||||
switch (type) {
|
||||
case QtDebugMsg:
|
||||
|
@ -79,7 +76,6 @@ void LogBrowserDialog::outputMessage(QtMsgType type, const QString &msg, const Q
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
void LogBrowserDialog::save()
|
||||
{
|
||||
QString saveFileName = QFileDialog::getSaveFileName(this,
|
||||
|
@ -95,8 +91,8 @@ void LogBrowserDialog::save()
|
|||
QMessageBox::warning(this,
|
||||
tr("Error"),
|
||||
QString(tr("<nobr>File '%1'<br/>cannot be opened for writing.<br/><br/>"
|
||||
"The log output could <b>not</b> be saved!</nobr>"))
|
||||
.arg(saveFileName));
|
||||
"The log output could <b>not</b> be saved!</nobr>"))
|
||||
.arg(saveFileName));
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -105,7 +101,7 @@ void LogBrowserDialog::save()
|
|||
file.close();
|
||||
}
|
||||
|
||||
void LogBrowserDialog::closeEvent(QCloseEvent *e)
|
||||
void LogBrowserDialog::closeEvent(QCloseEvent* e)
|
||||
{
|
||||
if (0 == DocumentWindow::total()) {
|
||||
e->accept();
|
||||
|
@ -115,7 +111,7 @@ void LogBrowserDialog::closeEvent(QCloseEvent *e)
|
|||
hide();
|
||||
}
|
||||
|
||||
void LogBrowserDialog::keyPressEvent(QKeyEvent *e)
|
||||
void LogBrowserDialog::keyPressEvent(QKeyEvent* e)
|
||||
{
|
||||
e->ignore();
|
||||
}
|
||||
|
|
|
@ -6,26 +6,25 @@
|
|||
class QTextBrowser;
|
||||
class QPushButton;
|
||||
|
||||
class LogBrowserDialog : public QDialog
|
||||
{
|
||||
class LogBrowserDialog : public QDialog {
|
||||
Q_OBJECT
|
||||
public:
|
||||
LogBrowserDialog(QWidget *parent = 0);
|
||||
LogBrowserDialog(QWidget* parent = 0);
|
||||
~LogBrowserDialog();
|
||||
|
||||
public slots:
|
||||
void outputMessage(QtMsgType type, const QString &msg, const QString &source, int line);
|
||||
void outputMessage(QtMsgType type, const QString& msg, const QString& source, int line);
|
||||
|
||||
protected slots:
|
||||
void save();
|
||||
|
||||
protected:
|
||||
virtual void keyPressEvent(QKeyEvent *e);
|
||||
virtual void closeEvent(QCloseEvent *e);
|
||||
virtual void keyPressEvent(QKeyEvent* e);
|
||||
virtual void closeEvent(QCloseEvent* e);
|
||||
|
||||
QTextBrowser *m_browser;
|
||||
QPushButton *m_clearButton;
|
||||
QPushButton *m_saveButton;
|
||||
QTextBrowser* m_browser;
|
||||
QPushButton* m_clearButton;
|
||||
QPushButton* m_saveButton;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
@ -1,15 +1,15 @@
|
|||
#include <QApplication>
|
||||
#include <QSurfaceFormat>
|
||||
#include <QDebug>
|
||||
#include <iostream>
|
||||
#include <cstdio>
|
||||
#include <dust3d/base/string.h>
|
||||
#include "document_window.h"
|
||||
#include "document.h"
|
||||
#include "document_window.h"
|
||||
#include "theme.h"
|
||||
#include "version.h"
|
||||
#include <QApplication>
|
||||
#include <QDebug>
|
||||
#include <QSurfaceFormat>
|
||||
#include <cstdio>
|
||||
#include <dust3d/base/string.h>
|
||||
#include <iostream>
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
int main(int argc, char* argv[])
|
||||
{
|
||||
QApplication app(argc, argv);
|
||||
|
||||
|
@ -27,15 +27,14 @@ int main(int argc, char *argv[])
|
|||
//freopen("dust3d.log", "w", stdout);
|
||||
//setvbuf(stdout, 0, _IONBF, 0);
|
||||
|
||||
DocumentWindow *firstWindow = DocumentWindow::createDocumentWindow();
|
||||
DocumentWindow* firstWindow = DocumentWindow::createDocumentWindow();
|
||||
|
||||
QStringList openFileList;
|
||||
QStringList waitingExportList;
|
||||
bool toggleColor = false;
|
||||
for (int i = 1; i < argc; ++i) {
|
||||
if ('-' == argv[i][0]) {
|
||||
if (0 == strcmp(argv[i], "-output") ||
|
||||
0 == strcmp(argv[i], "-o")) {
|
||||
if (0 == strcmp(argv[i], "-output") || 0 == strcmp(argv[i], "-o")) {
|
||||
++i;
|
||||
if (i < argc)
|
||||
waitingExportList.append(argv[i]);
|
||||
|
@ -60,7 +59,7 @@ int main(int argc, char *argv[])
|
|||
int totalExportFileNum = 0;
|
||||
int succeedExportNum = 0;
|
||||
int exitCode = -1;
|
||||
std::vector<DocumentWindow *> windowList;
|
||||
std::vector<DocumentWindow*> windowList;
|
||||
auto checkToSafelyExit = [&]() {
|
||||
if (-1 == exitCode)
|
||||
return;
|
||||
|
@ -76,17 +75,16 @@ int main(int argc, char *argv[])
|
|||
windowList.push_back(DocumentWindow::createDocumentWindow());
|
||||
}
|
||||
if (toggleColor) {
|
||||
for (auto &it: windowList)
|
||||
for (auto& it : windowList)
|
||||
it->toggleRenderColor();
|
||||
}
|
||||
if (!waitingExportList.empty() &&
|
||||
openFileList.size() == 1) {
|
||||
if (!waitingExportList.empty() && openFileList.size() == 1) {
|
||||
totalExportFileNum = openFileList.size() * waitingExportList.size();
|
||||
for (int i = 0; i < openFileList.size(); ++i) {
|
||||
QObject::connect(windowList[i], &DocumentWindow::workingStatusChanged, &app, checkToSafelyExit);
|
||||
}
|
||||
for (int i = 0; i < openFileList.size(); ++i) {
|
||||
QObject::connect(windowList[i], &DocumentWindow::waitingExportFinished, &app, [&](const QString &filename, bool isSuccessful) {
|
||||
QObject::connect(windowList[i], &DocumentWindow::waitingExportFinished, &app, [&](const QString& filename, bool isSuccessful) {
|
||||
qDebug() << "Export to" << filename << (isSuccessful ? "isSuccessful" : "failed");
|
||||
++finishedExportFileNum;
|
||||
if (isSuccessful)
|
||||
|
|
|
@ -1,21 +1,21 @@
|
|||
#include "material.h"
|
||||
#include "image_forever.h"
|
||||
|
||||
void initializeMaterialTexturesFromSnapshot(const dust3d::Snapshot &snapshot,
|
||||
const dust3d::Uuid &materialId,
|
||||
MaterialTextures &materialTextures,
|
||||
float &tileScale)
|
||||
void initializeMaterialTexturesFromSnapshot(const dust3d::Snapshot& snapshot,
|
||||
const dust3d::Uuid& materialId,
|
||||
MaterialTextures& materialTextures,
|
||||
float& tileScale)
|
||||
{
|
||||
auto materialIdString = materialId.toString();
|
||||
for (const auto &materialItem: snapshot.materials) {
|
||||
for (const auto& materialItem : snapshot.materials) {
|
||||
if (materialIdString != dust3d::String::valueOrEmpty(materialItem.first, "id"))
|
||||
continue;
|
||||
for (const auto &layer: materialItem.second) {
|
||||
for (const auto& layer : materialItem.second) {
|
||||
//FIXME: Only support one layer currently
|
||||
auto findTileScale = layer.first.find("tileScale");
|
||||
if (findTileScale != layer.first.end())
|
||||
tileScale = dust3d::String::toFloat(findTileScale->second);
|
||||
for (const auto &mapItem: layer.second) {
|
||||
for (const auto& mapItem : layer.second) {
|
||||
auto textureType = dust3d::TextureTypeFromString(dust3d::String::valueOrEmpty(mapItem, "for").c_str());
|
||||
if (textureType != dust3d::TextureType::None) {
|
||||
int index = (int)textureType - 1;
|
||||
|
|
|
@ -2,18 +2,17 @@
|
|||
#define DUST3D_APPLICATION_MATERIAL_H_
|
||||
|
||||
#include <QImage>
|
||||
#include <dust3d/base/uuid.h>
|
||||
#include <dust3d/base/texture_type.h>
|
||||
#include <dust3d/base/snapshot.h>
|
||||
#include <dust3d/base/texture_type.h>
|
||||
#include <dust3d/base/uuid.h>
|
||||
|
||||
struct MaterialTextures
|
||||
{
|
||||
const QImage *textureImages[(int)dust3d::TextureType::Count - 1] = {nullptr};
|
||||
struct MaterialTextures {
|
||||
const QImage* textureImages[(int)dust3d::TextureType::Count - 1] = { nullptr };
|
||||
};
|
||||
|
||||
void initializeMaterialTexturesFromSnapshot(const dust3d::Snapshot &snapshot,
|
||||
const dust3d::Uuid &materialId,
|
||||
MaterialTextures &materialTextures,
|
||||
float &tileScale);
|
||||
void initializeMaterialTexturesFromSnapshot(const dust3d::Snapshot& snapshot,
|
||||
const dust3d::Uuid& materialId,
|
||||
MaterialTextures& materialTextures,
|
||||
float& tileScale);
|
||||
|
||||
#endif
|
||||
|
|
|
@ -1,46 +1,46 @@
|
|||
#include <QVBoxLayout>
|
||||
#include <QHBoxLayout>
|
||||
#include <QGridLayout>
|
||||
#include "material_edit_widget.h"
|
||||
#include "document.h"
|
||||
#include "float_number_widget.h"
|
||||
#include "horizontal_line_widget.h"
|
||||
#include "image_forever.h"
|
||||
#include "theme.h"
|
||||
#include "version.h"
|
||||
#include <QFileDialog>
|
||||
#include <QFormLayout>
|
||||
#include <QGridLayout>
|
||||
#include <QMenu>
|
||||
#include <QWidgetAction>
|
||||
#include <QLineEdit>
|
||||
#include <QMessageBox>
|
||||
#include <QFileDialog>
|
||||
#include <QHBoxLayout>
|
||||
#include <QLabel>
|
||||
#include <QLineEdit>
|
||||
#include <QMenu>
|
||||
#include <QMessageBox>
|
||||
#include <QThread>
|
||||
#include "theme.h"
|
||||
#include "material_edit_widget.h"
|
||||
#include "float_number_widget.h"
|
||||
#include "version.h"
|
||||
#include "image_forever.h"
|
||||
#include "document.h"
|
||||
#include "horizontal_line_widget.h"
|
||||
#include <QVBoxLayout>
|
||||
#include <QWidgetAction>
|
||||
|
||||
ImagePreviewWidget *MaterialEditWidget::createMapButton()
|
||||
ImagePreviewWidget* MaterialEditWidget::createMapButton()
|
||||
{
|
||||
ImagePreviewWidget *mapButton = new ImagePreviewWidget;
|
||||
ImagePreviewWidget* mapButton = new ImagePreviewWidget;
|
||||
mapButton->setFixedSize(Theme::partPreviewImageSize * 2, Theme::partPreviewImageSize * 2);
|
||||
updateMapButtonBackground(mapButton, nullptr);
|
||||
return mapButton;
|
||||
}
|
||||
|
||||
QImage *MaterialEditWidget::pickImage()
|
||||
QImage* MaterialEditWidget::pickImage()
|
||||
{
|
||||
QString fileName = QFileDialog::getOpenFileName(this, QString(), QString(),
|
||||
tr("Image Files (*.png *.jpg *.bmp)")).trimmed();
|
||||
tr("Image Files (*.png *.jpg *.bmp)"))
|
||||
.trimmed();
|
||||
if (fileName.isEmpty())
|
||||
return nullptr;
|
||||
QImage *image = new QImage();
|
||||
QImage* image = new QImage();
|
||||
if (!image->load(fileName))
|
||||
return nullptr;
|
||||
return image;
|
||||
}
|
||||
|
||||
MaterialEditWidget::MaterialEditWidget(const Document *document, QWidget *parent) :
|
||||
QDialog(parent),
|
||||
m_document(document)
|
||||
MaterialEditWidget::MaterialEditWidget(const Document* document, QWidget* parent)
|
||||
: QDialog(parent)
|
||||
, m_document(document)
|
||||
{
|
||||
setWindowFlags(windowFlags() | Qt::WindowStaysOnTopHint);
|
||||
|
||||
|
@ -56,19 +56,19 @@ MaterialEditWidget::MaterialEditWidget(const Document *document, QWidget *parent
|
|||
nameFont.setWeight(QFont::Light);
|
||||
nameFont.setBold(false);
|
||||
|
||||
QGridLayout *mapLayout = new QGridLayout;
|
||||
QGridLayout* mapLayout = new QGridLayout;
|
||||
int row = 0;
|
||||
int col = 0;
|
||||
for (int i = 1; i < (int)dust3d::TextureType::Count; i++) {
|
||||
QVBoxLayout *textureManageLayout = new QVBoxLayout;
|
||||
QVBoxLayout* textureManageLayout = new QVBoxLayout;
|
||||
|
||||
MaterialMap item;
|
||||
item.forWhat = (dust3d::TextureType)i;
|
||||
m_layers[0].maps.push_back(item);
|
||||
|
||||
ImagePreviewWidget *imageButton = createMapButton();
|
||||
ImagePreviewWidget* imageButton = createMapButton();
|
||||
connect(imageButton, &ImagePreviewWidget::clicked, [=]() {
|
||||
QImage *image = pickImage();
|
||||
QImage* image = pickImage();
|
||||
if (nullptr == image)
|
||||
return;
|
||||
m_layers[0].maps[(int)i - 1].imageId = ImageForever::add(image);
|
||||
|
@ -77,10 +77,10 @@ MaterialEditWidget::MaterialEditWidget(const Document *document, QWidget *parent
|
|||
emit layersAdjusted();
|
||||
});
|
||||
|
||||
QLabel *nameLabel = new QLabel(tr(dust3d::TextureTypeToDispName(item.forWhat).c_str()));
|
||||
QLabel* nameLabel = new QLabel(tr(dust3d::TextureTypeToDispName(item.forWhat).c_str()));
|
||||
nameLabel->setFont(nameFont);
|
||||
|
||||
QPushButton *eraser = new QPushButton(QChar(fa::eraser));
|
||||
QPushButton* eraser = new QPushButton(QChar(fa::eraser));
|
||||
Theme::initAwesomeToolButton(eraser);
|
||||
|
||||
connect(eraser, &QPushButton::clicked, [=]() {
|
||||
|
@ -89,7 +89,7 @@ MaterialEditWidget::MaterialEditWidget(const Document *document, QWidget *parent
|
|||
emit layersAdjusted();
|
||||
});
|
||||
|
||||
QHBoxLayout *textureTitleLayout = new QHBoxLayout;
|
||||
QHBoxLayout* textureTitleLayout = new QHBoxLayout;
|
||||
textureTitleLayout->addWidget(eraser);
|
||||
textureTitleLayout->addWidget(nameLabel);
|
||||
textureTitleLayout->addStretch();
|
||||
|
@ -105,12 +105,12 @@ MaterialEditWidget::MaterialEditWidget(const Document *document, QWidget *parent
|
|||
}
|
||||
}
|
||||
|
||||
QVBoxLayout *rightLayout = new QVBoxLayout;
|
||||
QVBoxLayout* rightLayout = new QVBoxLayout;
|
||||
rightLayout->addStretch();
|
||||
rightLayout->addLayout(mapLayout);
|
||||
rightLayout->addStretch();
|
||||
|
||||
QHBoxLayout *paramtersLayout = new QHBoxLayout;
|
||||
QHBoxLayout* paramtersLayout = new QHBoxLayout;
|
||||
paramtersLayout->setContentsMargins(256, 0, 0, 0);
|
||||
paramtersLayout->addStretch();
|
||||
paramtersLayout->addLayout(rightLayout);
|
||||
|
@ -120,11 +120,11 @@ MaterialEditWidget::MaterialEditWidget(const Document *document, QWidget *parent
|
|||
m_unsaved = true;
|
||||
updateTitle();
|
||||
});
|
||||
QPushButton *saveButton = new QPushButton(tr("Save"));
|
||||
QPushButton* saveButton = new QPushButton(tr("Save"));
|
||||
connect(saveButton, &QPushButton::clicked, this, &MaterialEditWidget::save);
|
||||
saveButton->setDefault(true);
|
||||
|
||||
FloatNumberWidget *tileScaleWidget = new FloatNumberWidget;
|
||||
FloatNumberWidget* tileScaleWidget = new FloatNumberWidget;
|
||||
tileScaleWidget->setItemName(tr("Tile Scale"));
|
||||
tileScaleWidget->setRange(0.01, 1.0);
|
||||
tileScaleWidget->setValue(m_layers[0].tileScale);
|
||||
|
@ -136,25 +136,25 @@ MaterialEditWidget::MaterialEditWidget(const Document *document, QWidget *parent
|
|||
emit layersAdjusted();
|
||||
});
|
||||
|
||||
QPushButton *tileScaleEraser = new QPushButton(QChar(fa::eraser));
|
||||
QPushButton* tileScaleEraser = new QPushButton(QChar(fa::eraser));
|
||||
Theme::initAwesomeToolButton(tileScaleEraser);
|
||||
|
||||
connect(tileScaleEraser, &QPushButton::clicked, [=]() {
|
||||
tileScaleWidget->setValue(1.0);
|
||||
});
|
||||
|
||||
QHBoxLayout *tileScaleLayout = new QHBoxLayout;
|
||||
QHBoxLayout* tileScaleLayout = new QHBoxLayout;
|
||||
tileScaleLayout->addWidget(tileScaleEraser);
|
||||
tileScaleLayout->addWidget(tileScaleWidget);
|
||||
tileScaleLayout->addStretch();
|
||||
|
||||
QHBoxLayout *baseInfoLayout = new QHBoxLayout;
|
||||
QHBoxLayout* baseInfoLayout = new QHBoxLayout;
|
||||
baseInfoLayout->addWidget(new QLabel(tr("Name")));
|
||||
baseInfoLayout->addWidget(m_nameEdit);
|
||||
baseInfoLayout->addStretch();
|
||||
baseInfoLayout->addWidget(saveButton);
|
||||
|
||||
QVBoxLayout *mainLayout = new QVBoxLayout;
|
||||
QVBoxLayout* mainLayout = new QVBoxLayout;
|
||||
mainLayout->addLayout(paramtersLayout);
|
||||
mainLayout->addStretch();
|
||||
mainLayout->addWidget(new HorizontalLineWidget());
|
||||
|
@ -176,7 +176,7 @@ MaterialEditWidget::MaterialEditWidget(const Document *document, QWidget *parent
|
|||
updateTitle();
|
||||
}
|
||||
|
||||
void MaterialEditWidget::updateMapButtonBackground(ImagePreviewWidget *button, const QImage *image)
|
||||
void MaterialEditWidget::updateMapButtonBackground(ImagePreviewWidget* button, const QImage* image)
|
||||
{
|
||||
if (nullptr == image)
|
||||
button->updateImage(QImage());
|
||||
|
@ -189,7 +189,7 @@ void MaterialEditWidget::reject()
|
|||
close();
|
||||
}
|
||||
|
||||
void MaterialEditWidget::closeEvent(QCloseEvent *event)
|
||||
void MaterialEditWidget::closeEvent(QCloseEvent* event)
|
||||
{
|
||||
if (m_unsaved && !m_closed) {
|
||||
QMessageBox::StandardButton answer = QMessageBox::question(this,
|
||||
|
@ -235,7 +235,7 @@ void MaterialEditWidget::updatePreview()
|
|||
|
||||
qDebug() << "Material preview generating..";
|
||||
|
||||
QThread *thread = new QThread;
|
||||
QThread* thread = new QThread;
|
||||
m_materialPreviewsGenerator = new MaterialPreviewsGenerator();
|
||||
m_materialPreviewsGenerator->addMaterial(dust3d::Uuid(), m_layers);
|
||||
m_materialPreviewsGenerator->moveToThread(thread);
|
||||
|
@ -279,7 +279,7 @@ void MaterialEditWidget::updateTitle()
|
|||
setWindowTitle(applicationTitle(tr("New") + (m_unsaved ? "*" : "")));
|
||||
return;
|
||||
}
|
||||
const Material *material = m_document->findMaterial(m_materialId);
|
||||
const Material* material = m_document->findMaterial(m_materialId);
|
||||
if (nullptr == material) {
|
||||
qDebug() << "Find material failed:" << m_materialId;
|
||||
return;
|
||||
|
@ -299,9 +299,9 @@ void MaterialEditWidget::setEditMaterialLayers(std::vector<MaterialLayer> layers
|
|||
m_layers[0].maps[i - 1].imageId = dust3d::Uuid();
|
||||
}
|
||||
if (!layers.empty()) {
|
||||
for (const auto &layer: layers) {
|
||||
for (const auto& layer : layers) {
|
||||
m_layers[0].tileScale = layer.tileScale;
|
||||
for (const auto &mapItem: layer.maps) {
|
||||
for (const auto& mapItem : layer.maps) {
|
||||
int index = (int)mapItem.forWhat - 1;
|
||||
if (index >= 0 && index < (int)dust3d::TextureType::Count - 1) {
|
||||
m_layers[0].maps[index].imageId = mapItem.imageId;
|
||||
|
|
|
@ -1,26 +1,24 @@
|
|||
#ifndef DUST3D_APPLICATION_MATERIAL_EDIT_WIDGET_H_
|
||||
#define DUST3D_APPLICATION_MATERIAL_EDIT_WIDGET_H_
|
||||
|
||||
#include <QDialog>
|
||||
#include <map>
|
||||
#include <QCloseEvent>
|
||||
#include <QLineEdit>
|
||||
#include "model_widget.h"
|
||||
#include "material_previews_generator.h"
|
||||
#include "image_preview_widget.h"
|
||||
#include "float_number_widget.h"
|
||||
#include "image_preview_widget.h"
|
||||
#include "material_layer.h"
|
||||
#include "material_previews_generator.h"
|
||||
#include "model_widget.h"
|
||||
#include <QCloseEvent>
|
||||
#include <QDialog>
|
||||
#include <QLineEdit>
|
||||
#include <map>
|
||||
|
||||
class Document;
|
||||
|
||||
enum class PopupWidgetType
|
||||
{
|
||||
enum class PopupWidgetType {
|
||||
PitchYawRoll,
|
||||
Intersection
|
||||
};
|
||||
|
||||
class MaterialEditWidget : public QDialog
|
||||
{
|
||||
class MaterialEditWidget : public QDialog {
|
||||
Q_OBJECT
|
||||
signals:
|
||||
void addMaterial(dust3d::Uuid materialId, QString name, std::vector<MaterialLayer> layers);
|
||||
|
@ -28,8 +26,9 @@ signals:
|
|||
void setMaterialLayers(dust3d::Uuid materialId, std::vector<MaterialLayer> layers);
|
||||
void renameMaterial(dust3d::Uuid materialId, QString name);
|
||||
void layersAdjusted();
|
||||
|
||||
public:
|
||||
MaterialEditWidget(const Document *document, QWidget *parent=nullptr);
|
||||
MaterialEditWidget(const Document* document, QWidget* parent = nullptr);
|
||||
~MaterialEditWidget();
|
||||
public slots:
|
||||
void updatePreview();
|
||||
|
@ -40,25 +39,27 @@ public slots:
|
|||
void save();
|
||||
void clearUnsaveState();
|
||||
void previewReady();
|
||||
|
||||
protected:
|
||||
QSize sizeHint() const override;
|
||||
void closeEvent(QCloseEvent *event) override;
|
||||
void closeEvent(QCloseEvent* event) override;
|
||||
void reject() override;
|
||||
|
||||
private:
|
||||
void updateMapButtonBackground(ImagePreviewWidget *button, const QImage *image);
|
||||
ImagePreviewWidget *createMapButton();
|
||||
QImage *pickImage();
|
||||
const Document *m_document = nullptr;
|
||||
MaterialPreviewsGenerator *m_materialPreviewsGenerator = nullptr;
|
||||
ModelWidget *m_previewWidget = nullptr;
|
||||
FloatNumberWidget *m_tileScaleSlider = nullptr;
|
||||
void updateMapButtonBackground(ImagePreviewWidget* button, const QImage* image);
|
||||
ImagePreviewWidget* createMapButton();
|
||||
QImage* pickImage();
|
||||
const Document* m_document = nullptr;
|
||||
MaterialPreviewsGenerator* m_materialPreviewsGenerator = nullptr;
|
||||
ModelWidget* m_previewWidget = nullptr;
|
||||
FloatNumberWidget* m_tileScaleSlider = nullptr;
|
||||
bool m_isPreviewDirty = false;
|
||||
bool m_closed = false;
|
||||
dust3d::Uuid m_materialId;
|
||||
bool m_unsaved = false;
|
||||
QLineEdit *m_nameEdit = nullptr;
|
||||
QLineEdit* m_nameEdit = nullptr;
|
||||
std::vector<MaterialLayer> m_layers;
|
||||
ImagePreviewWidget *m_textureMapButtons[(int)dust3d::TextureType::Count - 1] = {nullptr};
|
||||
ImagePreviewWidget* m_textureMapButtons[(int)dust3d::TextureType::Count - 1] = { nullptr };
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
@ -1,19 +1,17 @@
|
|||
#ifndef DUST3D_APPLICATION_MATERIAL_LAYER_H_
|
||||
#define DUST3D_APPLICATION_MATERIAL_LAYER_H_
|
||||
|
||||
#include <vector>
|
||||
#include <dust3d/base/texture_type.h>
|
||||
#include <dust3d/base/uuid.h>
|
||||
#include <vector>
|
||||
|
||||
class MaterialMap
|
||||
{
|
||||
class MaterialMap {
|
||||
public:
|
||||
dust3d::TextureType forWhat;
|
||||
dust3d::Uuid imageId;
|
||||
};
|
||||
|
||||
class MaterialLayer
|
||||
{
|
||||
class MaterialLayer {
|
||||
public:
|
||||
std::vector<MaterialMap> maps;
|
||||
float tileScale = 1.0;
|
||||
|
|
|
@ -1,15 +1,15 @@
|
|||
#include "material_list_widget.h"
|
||||
#include "document.h"
|
||||
#include <QApplication>
|
||||
#include <QClipboard>
|
||||
#include <QGuiApplication>
|
||||
#include <QMenu>
|
||||
#include <QXmlStreamWriter>
|
||||
#include <QClipboard>
|
||||
#include <QApplication>
|
||||
#include <dust3d/base/snapshot_xml.h>
|
||||
#include "material_list_widget.h"
|
||||
#include "document.h"
|
||||
|
||||
MaterialListWidget::MaterialListWidget(const Document *document, QWidget *parent) :
|
||||
QTreeWidget(parent),
|
||||
m_document(document)
|
||||
MaterialListWidget::MaterialListWidget(const Document* document, QWidget* parent)
|
||||
: QTreeWidget(parent)
|
||||
, m_document(document)
|
||||
{
|
||||
setVerticalScrollMode(QAbstractItemView::ScrollPerPixel);
|
||||
setFocusPolicy(Qt::NoFocus);
|
||||
|
@ -59,7 +59,7 @@ void MaterialListWidget::updateMaterialSelectState(dust3d::Uuid materialId, bool
|
|||
qDebug() << "Find material item failed:" << materialId;
|
||||
return;
|
||||
}
|
||||
MaterialWidget *materialWidget = (MaterialWidget *)itemWidget(findItemResult->second.first, findItemResult->second.second);
|
||||
MaterialWidget* materialWidget = (MaterialWidget*)itemWidget(findItemResult->second.first, findItemResult->second.second);
|
||||
materialWidget->updateCheckedState(selected);
|
||||
}
|
||||
|
||||
|
@ -90,7 +90,7 @@ void MaterialListWidget::selectMaterial(dust3d::Uuid materialId, bool multiple)
|
|||
}
|
||||
}
|
||||
if (!m_selectedMaterialIds.empty()) {
|
||||
for (const auto &id: m_selectedMaterialIds) {
|
||||
for (const auto& id : m_selectedMaterialIds) {
|
||||
updateMaterialSelectState(id, false);
|
||||
}
|
||||
m_selectedMaterialIds.clear();
|
||||
|
@ -107,20 +107,20 @@ void MaterialListWidget::selectMaterial(dust3d::Uuid materialId, bool multiple)
|
|||
}
|
||||
}
|
||||
|
||||
void MaterialListWidget::mousePressEvent(QMouseEvent *event)
|
||||
void MaterialListWidget::mousePressEvent(QMouseEvent* event)
|
||||
{
|
||||
QModelIndex itemIndex = indexAt(event->pos());
|
||||
QTreeView::mousePressEvent(event);
|
||||
if (event->button() == Qt::LeftButton) {
|
||||
bool multiple = QGuiApplication::queryKeyboardModifiers().testFlag(Qt::ControlModifier);
|
||||
if (itemIndex.isValid()) {
|
||||
QTreeWidgetItem *item = itemFromIndex(itemIndex);
|
||||
QTreeWidgetItem* item = itemFromIndex(itemIndex);
|
||||
auto materialId = dust3d::Uuid(item->data(itemIndex.column(), Qt::UserRole).toString().toUtf8().constData());
|
||||
if (QGuiApplication::queryKeyboardModifiers().testFlag(Qt::ShiftModifier)) {
|
||||
bool startAdd = false;
|
||||
bool stopAdd = false;
|
||||
std::vector<dust3d::Uuid> waitQueue;
|
||||
for (const auto &childId: m_document->materialIdList) {
|
||||
for (const auto& childId : m_document->materialIdList) {
|
||||
if (m_shiftStartMaterialId == childId || materialId == childId) {
|
||||
if (startAdd) {
|
||||
stopAdd = true;
|
||||
|
@ -135,7 +135,7 @@ void MaterialListWidget::mousePressEvent(QMouseEvent *event)
|
|||
}
|
||||
if (stopAdd && !waitQueue.empty()) {
|
||||
if (!m_selectedMaterialIds.empty()) {
|
||||
for (const auto &id: m_selectedMaterialIds) {
|
||||
for (const auto& id : m_selectedMaterialIds) {
|
||||
updateMaterialSelectState(id, false);
|
||||
}
|
||||
m_selectedMaterialIds.clear();
|
||||
|
@ -143,7 +143,7 @@ void MaterialListWidget::mousePressEvent(QMouseEvent *event)
|
|||
if (!m_currentSelectedMaterialId.isNull()) {
|
||||
m_currentSelectedMaterialId = dust3d::Uuid();
|
||||
}
|
||||
for (const auto &waitId: waitQueue) {
|
||||
for (const auto& waitId : waitQueue) {
|
||||
selectMaterial(waitId, true);
|
||||
}
|
||||
}
|
||||
|
@ -161,11 +161,10 @@ void MaterialListWidget::mousePressEvent(QMouseEvent *event)
|
|||
|
||||
bool MaterialListWidget::isMaterialSelected(dust3d::Uuid materialId)
|
||||
{
|
||||
return (m_currentSelectedMaterialId == materialId ||
|
||||
m_selectedMaterialIds.find(materialId) != m_selectedMaterialIds.end());
|
||||
return (m_currentSelectedMaterialId == materialId || m_selectedMaterialIds.find(materialId) != m_selectedMaterialIds.end());
|
||||
}
|
||||
|
||||
void MaterialListWidget::showContextMenu(const QPoint &pos)
|
||||
void MaterialListWidget::showContextMenu(const QPoint& pos)
|
||||
{
|
||||
if (!m_hasContextMenu)
|
||||
return;
|
||||
|
@ -177,7 +176,7 @@ void MaterialListWidget::showContextMenu(const QPoint &pos)
|
|||
unorderedMaterialIds.insert(m_currentSelectedMaterialId);
|
||||
|
||||
std::vector<dust3d::Uuid> materialIds;
|
||||
for (const auto &cand: m_document->materialIdList) {
|
||||
for (const auto& cand : m_document->materialIdList) {
|
||||
if (unorderedMaterialIds.find(cand) != unorderedMaterialIds.end())
|
||||
materialIds.push_back(cand);
|
||||
}
|
||||
|
@ -205,7 +204,7 @@ void MaterialListWidget::showContextMenu(const QPoint &pos)
|
|||
QAction deleteAction(tr("Delete"), this);
|
||||
if (!materialIds.empty()) {
|
||||
connect(&deleteAction, &QAction::triggered, [=]() {
|
||||
for (const auto &materialId: materialIds)
|
||||
for (const auto& materialId : materialIds)
|
||||
emit removeMaterial(materialId);
|
||||
});
|
||||
contextMenu.addAction(&deleteAction);
|
||||
|
@ -214,7 +213,7 @@ void MaterialListWidget::showContextMenu(const QPoint &pos)
|
|||
contextMenu.exec(mapToGlobal(pos));
|
||||
}
|
||||
|
||||
void MaterialListWidget::resizeEvent(QResizeEvent *event)
|
||||
void MaterialListWidget::resizeEvent(QResizeEvent* event)
|
||||
{
|
||||
QTreeWidget::resizeEvent(event);
|
||||
if (calculateColumnCount() != columnCount())
|
||||
|
@ -249,9 +248,9 @@ void MaterialListWidget::reload()
|
|||
setColumnWidth(i, columnWidth);
|
||||
|
||||
std::vector<dust3d::Uuid> orderedMaterialIdList = m_document->materialIdList;
|
||||
std::sort(orderedMaterialIdList.begin(), orderedMaterialIdList.end(), [&](const dust3d::Uuid &firstMaterialId, const dust3d::Uuid &secondMaterialId) {
|
||||
const auto *firstMaterial = m_document->findMaterial(firstMaterialId);
|
||||
const auto *secondMaterial = m_document->findMaterial(secondMaterialId);
|
||||
std::sort(orderedMaterialIdList.begin(), orderedMaterialIdList.end(), [&](const dust3d::Uuid& firstMaterialId, const dust3d::Uuid& secondMaterialId) {
|
||||
const auto* firstMaterial = m_document->findMaterial(firstMaterialId);
|
||||
const auto* secondMaterial = m_document->findMaterial(secondMaterialId);
|
||||
if (nullptr == firstMaterial || nullptr == secondMaterial)
|
||||
return false;
|
||||
return QString::compare(firstMaterial->name, secondMaterial->name, Qt::CaseInsensitive) < 0;
|
||||
|
@ -259,13 +258,13 @@ void MaterialListWidget::reload()
|
|||
|
||||
decltype(orderedMaterialIdList.size()) materialIndex = 0;
|
||||
while (materialIndex < orderedMaterialIdList.size()) {
|
||||
QTreeWidgetItem *item = new QTreeWidgetItem(this);
|
||||
QTreeWidgetItem* item = new QTreeWidgetItem(this);
|
||||
item->setFlags((item->flags() | Qt::ItemIsEnabled) & ~(Qt::ItemIsSelectable) & ~(Qt::ItemIsEditable));
|
||||
for (int col = 0; col < columns && materialIndex < orderedMaterialIdList.size(); col++, materialIndex++) {
|
||||
const auto &materialId = orderedMaterialIdList[materialIndex];
|
||||
const auto& materialId = orderedMaterialIdList[materialIndex];
|
||||
item->setSizeHint(col, QSize(columnWidth, MaterialWidget::preferredHeight() + 2));
|
||||
item->setData(col, Qt::UserRole, QString(materialId.toString().c_str()));
|
||||
MaterialWidget *widget = new MaterialWidget(m_document, materialId);
|
||||
MaterialWidget* widget = new MaterialWidget(m_document, materialId);
|
||||
connect(widget, &MaterialWidget::modifyMaterial, this, &MaterialListWidget::modifyMaterial);
|
||||
setItemWidget(item, col, widget);
|
||||
widget->reload();
|
||||
|
@ -304,6 +303,6 @@ void MaterialListWidget::copy()
|
|||
|
||||
std::string snapshotXml;
|
||||
dust3d::saveSnapshotToXmlString(snapshot, snapshotXml);
|
||||
QClipboard *clipboard = QApplication::clipboard();
|
||||
QClipboard* clipboard = QApplication::clipboard();
|
||||
clipboard->setText(snapshotXml.c_str());
|
||||
}
|
||||
|
|
|
@ -1,41 +1,43 @@
|
|||
#ifndef DUST3D_APPLICATION_MATERIAL_LIST_WIDGET_H_
|
||||
#define DUST3D_APPLICATION_MATERIAL_LIST_WIDGET_H_
|
||||
|
||||
#include "material_widget.h"
|
||||
#include <QMouseEvent>
|
||||
#include <QTreeWidget>
|
||||
#include <map>
|
||||
#include <QMouseEvent>
|
||||
#include "material_widget.h"
|
||||
|
||||
class Document;
|
||||
|
||||
class MaterialListWidget : public QTreeWidget
|
||||
{
|
||||
class MaterialListWidget : public QTreeWidget {
|
||||
Q_OBJECT
|
||||
signals:
|
||||
void removeMaterial(dust3d::Uuid materialId);
|
||||
void modifyMaterial(dust3d::Uuid materialId);
|
||||
void cornerButtonClicked(dust3d::Uuid materialId);
|
||||
void currentSelectedMaterialChanged(dust3d::Uuid materialId);
|
||||
|
||||
public:
|
||||
MaterialListWidget(const Document *document, QWidget *parent=nullptr);
|
||||
MaterialListWidget(const Document* document, QWidget* parent = nullptr);
|
||||
bool isMaterialSelected(dust3d::Uuid materialId);
|
||||
void enableMultipleSelection(bool enabled);
|
||||
public slots:
|
||||
void reload();
|
||||
void removeAllContent();
|
||||
void materialRemoved(dust3d::Uuid materialId);
|
||||
void showContextMenu(const QPoint &pos);
|
||||
void selectMaterial(dust3d::Uuid materialId, bool multiple=false);
|
||||
void showContextMenu(const QPoint& pos);
|
||||
void selectMaterial(dust3d::Uuid materialId, bool multiple = false);
|
||||
void copy();
|
||||
void setHasContextMenu(bool hasContextMenu);
|
||||
|
||||
protected:
|
||||
void resizeEvent(QResizeEvent *event) override;
|
||||
void mousePressEvent(QMouseEvent *event) override;
|
||||
void resizeEvent(QResizeEvent* event) override;
|
||||
void mousePressEvent(QMouseEvent* event) override;
|
||||
|
||||
private:
|
||||
int calculateColumnCount();
|
||||
void updateMaterialSelectState(dust3d::Uuid materialId, bool selected);
|
||||
const Document *m_document = nullptr;
|
||||
std::map<dust3d::Uuid, std::pair<QTreeWidgetItem *, int>> m_itemMap;
|
||||
const Document* m_document = nullptr;
|
||||
std::map<dust3d::Uuid, std::pair<QTreeWidgetItem*, int>> m_itemMap;
|
||||
std::set<dust3d::Uuid> m_selectedMaterialIds;
|
||||
dust3d::Uuid m_currentSelectedMaterialId;
|
||||
dust3d::Uuid m_shiftStartMaterialId;
|
||||
|
|
|
@ -1,34 +1,34 @@
|
|||
#include <QHBoxLayout>
|
||||
#include <QVBoxLayout>
|
||||
#include <QPushButton>
|
||||
#include "material_manage_widget.h"
|
||||
#include "theme.h"
|
||||
#include "material_edit_widget.h"
|
||||
#include "info_label.h"
|
||||
#include "document.h"
|
||||
#include "info_label.h"
|
||||
#include "material_edit_widget.h"
|
||||
#include "theme.h"
|
||||
#include <QHBoxLayout>
|
||||
#include <QPushButton>
|
||||
#include <QVBoxLayout>
|
||||
|
||||
MaterialManageWidget::MaterialManageWidget(const Document *document, QWidget *parent) :
|
||||
QWidget(parent),
|
||||
m_document(document)
|
||||
MaterialManageWidget::MaterialManageWidget(const Document* document, QWidget* parent)
|
||||
: QWidget(parent)
|
||||
, m_document(document)
|
||||
{
|
||||
QPushButton *addMaterialButton = new QPushButton(Theme::awesome()->icon(fa::plus), tr("Add Material..."));
|
||||
QPushButton* addMaterialButton = new QPushButton(Theme::awesome()->icon(fa::plus), tr("Add Material..."));
|
||||
|
||||
connect(addMaterialButton, &QPushButton::clicked, this, &MaterialManageWidget::showAddMaterialDialog);
|
||||
|
||||
QHBoxLayout *toolsLayout = new QHBoxLayout;
|
||||
QHBoxLayout* toolsLayout = new QHBoxLayout;
|
||||
toolsLayout->addWidget(addMaterialButton);
|
||||
|
||||
m_materialListWidget = new MaterialListWidget(document);
|
||||
connect(m_materialListWidget, &MaterialListWidget::modifyMaterial, this, &MaterialManageWidget::showMaterialDialog);
|
||||
|
||||
QVBoxLayout *mainLayout = new QVBoxLayout;
|
||||
QVBoxLayout* mainLayout = new QVBoxLayout;
|
||||
mainLayout->addLayout(toolsLayout);
|
||||
mainLayout->addWidget(m_materialListWidget);
|
||||
|
||||
setLayout(mainLayout);
|
||||
}
|
||||
|
||||
MaterialListWidget *MaterialManageWidget::materialListWidget()
|
||||
MaterialListWidget* MaterialManageWidget::materialListWidget()
|
||||
{
|
||||
return m_materialListWidget;
|
||||
}
|
||||
|
@ -45,10 +45,10 @@ void MaterialManageWidget::showAddMaterialDialog()
|
|||
|
||||
void MaterialManageWidget::showMaterialDialog(dust3d::Uuid materialId)
|
||||
{
|
||||
MaterialEditWidget *materialEditWidget = new MaterialEditWidget(m_document);
|
||||
MaterialEditWidget* materialEditWidget = new MaterialEditWidget(m_document);
|
||||
materialEditWidget->setAttribute(Qt::WA_DeleteOnClose);
|
||||
if (!materialId.isNull()) {
|
||||
const Material *material = m_document->findMaterial(materialId);
|
||||
const Material* material = m_document->findMaterial(materialId);
|
||||
if (nullptr != material) {
|
||||
materialEditWidget->setEditMaterialId(materialId);
|
||||
materialEditWidget->setEditMaterialName(material->name);
|
||||
|
@ -58,7 +58,7 @@ void MaterialManageWidget::showMaterialDialog(dust3d::Uuid materialId)
|
|||
}
|
||||
materialEditWidget->show();
|
||||
connect(materialEditWidget, &QDialog::destroyed, [=]() {
|
||||
emit unregisterDialog((QWidget *)materialEditWidget);
|
||||
emit unregisterDialog((QWidget*)materialEditWidget);
|
||||
});
|
||||
emit registerDialog((QWidget *)materialEditWidget);
|
||||
emit registerDialog((QWidget*)materialEditWidget);
|
||||
}
|
||||
|
|
|
@ -1,28 +1,30 @@
|
|||
#ifndef DUST3D_APPLICATION_MATERIAL_MANAGE_WIDGET_H_
|
||||
#define DUST3D_APPLICATION_MATERIAL_MANAGE_WIDGET_H_
|
||||
|
||||
#include <QWidget>
|
||||
#include "material_list_widget.h"
|
||||
#include <QWidget>
|
||||
|
||||
class Document;
|
||||
|
||||
class MaterialManageWidget : public QWidget
|
||||
{
|
||||
class MaterialManageWidget : public QWidget {
|
||||
Q_OBJECT
|
||||
signals:
|
||||
void registerDialog(QWidget *widget);
|
||||
void unregisterDialog(QWidget *widget);
|
||||
void registerDialog(QWidget* widget);
|
||||
void unregisterDialog(QWidget* widget);
|
||||
|
||||
public:
|
||||
MaterialManageWidget(const Document *document, QWidget *parent=nullptr);
|
||||
MaterialListWidget *materialListWidget();
|
||||
MaterialManageWidget(const Document* document, QWidget* parent = nullptr);
|
||||
MaterialListWidget* materialListWidget();
|
||||
|
||||
protected:
|
||||
virtual QSize sizeHint() const;
|
||||
public slots:
|
||||
void showAddMaterialDialog();
|
||||
void showMaterialDialog(dust3d::Uuid materialId);
|
||||
|
||||
private:
|
||||
const Document *m_document = nullptr;
|
||||
MaterialListWidget *m_materialListWidget = nullptr;
|
||||
const Document* m_document = nullptr;
|
||||
MaterialListWidget* m_materialListWidget = nullptr;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
@ -1,14 +1,14 @@
|
|||
#include <QGuiApplication>
|
||||
#include <QElapsedTimer>
|
||||
#include "material_previews_generator.h"
|
||||
#include "image_forever.h"
|
||||
#include "mesh_generator.h"
|
||||
#include "mesh_result_post_processor.h"
|
||||
#include "texture_generator.h"
|
||||
#include <QDebug>
|
||||
#include <QElapsedTimer>
|
||||
#include <QFile>
|
||||
#include <QGuiApplication>
|
||||
#include <dust3d/base/ds3_file.h>
|
||||
#include <dust3d/base/snapshot_xml.h>
|
||||
#include "material_previews_generator.h"
|
||||
#include "mesh_generator.h"
|
||||
#include "texture_generator.h"
|
||||
#include "image_forever.h"
|
||||
#include "mesh_result_post_processor.h"
|
||||
|
||||
MaterialPreviewsGenerator::MaterialPreviewsGenerator()
|
||||
{
|
||||
|
@ -16,63 +16,63 @@ MaterialPreviewsGenerator::MaterialPreviewsGenerator()
|
|||
|
||||
MaterialPreviewsGenerator::~MaterialPreviewsGenerator()
|
||||
{
|
||||
for (auto &item: m_previews) {
|
||||
for (auto& item : m_previews) {
|
||||
delete item.second;
|
||||
}
|
||||
}
|
||||
|
||||
void MaterialPreviewsGenerator::addMaterial(dust3d::Uuid materialId, const std::vector<MaterialLayer> &layers)
|
||||
void MaterialPreviewsGenerator::addMaterial(dust3d::Uuid materialId, const std::vector<MaterialLayer>& layers)
|
||||
{
|
||||
m_materials.push_back({materialId, layers});
|
||||
m_materials.push_back({ materialId, layers });
|
||||
}
|
||||
|
||||
const std::set<dust3d::Uuid> &MaterialPreviewsGenerator::generatedPreviewMaterialIds()
|
||||
const std::set<dust3d::Uuid>& MaterialPreviewsGenerator::generatedPreviewMaterialIds()
|
||||
{
|
||||
return m_generatedMaterialIds;
|
||||
}
|
||||
|
||||
ModelMesh *MaterialPreviewsGenerator::takePreview(dust3d::Uuid materialId)
|
||||
ModelMesh* MaterialPreviewsGenerator::takePreview(dust3d::Uuid materialId)
|
||||
{
|
||||
ModelMesh *resultMesh = m_previews[materialId];
|
||||
ModelMesh* resultMesh = m_previews[materialId];
|
||||
m_previews[materialId] = nullptr;
|
||||
return resultMesh;
|
||||
}
|
||||
|
||||
void MaterialPreviewsGenerator::generate()
|
||||
{
|
||||
dust3d::Snapshot *snapshot = new dust3d::Snapshot;
|
||||
dust3d::Snapshot* snapshot = new dust3d::Snapshot;
|
||||
|
||||
QFile file(":/resources/material-demo-model.ds3");
|
||||
file.open(QFile::ReadOnly);
|
||||
QByteArray fileData = file.readAll();
|
||||
|
||||
std::vector<dust3d::Uuid> partIds;
|
||||
dust3d::Ds3FileReader ds3Reader((const std::uint8_t *)fileData.data(), fileData.size());
|
||||
dust3d::Ds3FileReader ds3Reader((const std::uint8_t*)fileData.data(), fileData.size());
|
||||
for (int i = 0; i < (int)ds3Reader.items().size(); ++i) {
|
||||
dust3d::Ds3ReaderItem item = ds3Reader.items().at(i);
|
||||
if (item.type == "model") {
|
||||
std::vector<std::uint8_t> data;
|
||||
ds3Reader.loadItem(item.name, &data);
|
||||
std::string xmlString((char *)data.data(), data.size());
|
||||
dust3d::loadSnapshotFromXmlString(snapshot, (char *)xmlString.c_str());
|
||||
for (const auto &item: snapshot->parts) {
|
||||
std::string xmlString((char*)data.data(), data.size());
|
||||
dust3d::loadSnapshotFromXmlString(snapshot, (char*)xmlString.c_str());
|
||||
for (const auto& item : snapshot->parts) {
|
||||
partIds.push_back(dust3d::Uuid(item.first));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
dust3d::MeshGenerator::GeneratedCacheContext *cacheContext = new dust3d::MeshGenerator::GeneratedCacheContext();
|
||||
MeshGenerator *meshGenerator = new MeshGenerator(snapshot);
|
||||
dust3d::MeshGenerator::GeneratedCacheContext* cacheContext = new dust3d::MeshGenerator::GeneratedCacheContext();
|
||||
MeshGenerator* meshGenerator = new MeshGenerator(snapshot);
|
||||
meshGenerator->setGeneratedCacheContext(cacheContext);
|
||||
|
||||
meshGenerator->generate();
|
||||
for (const auto &mirror: cacheContext->partMirrorIdMap) {
|
||||
for (const auto& mirror : cacheContext->partMirrorIdMap) {
|
||||
partIds.push_back(dust3d::Uuid(mirror.first));
|
||||
}
|
||||
|
||||
dust3d::Object *object = meshGenerator->takeObject();
|
||||
dust3d::Object* object = meshGenerator->takeObject();
|
||||
if (nullptr != object) {
|
||||
MeshResultPostProcessor *poseProcessor = new MeshResultPostProcessor(*object);
|
||||
MeshResultPostProcessor* poseProcessor = new MeshResultPostProcessor(*object);
|
||||
poseProcessor->poseProcess();
|
||||
delete object;
|
||||
object = poseProcessor->takePostProcessedObject();
|
||||
|
@ -80,14 +80,14 @@ void MaterialPreviewsGenerator::generate()
|
|||
}
|
||||
|
||||
if (nullptr != object) {
|
||||
for (const auto &material: m_materials) {
|
||||
TextureGenerator *textureGenerator = new TextureGenerator(*object);
|
||||
for (const auto &layer: material.second) {
|
||||
for (const auto &mapItem: layer.maps) {
|
||||
const QImage *image = ImageForever::get(mapItem.imageId);
|
||||
for (const auto& material : m_materials) {
|
||||
TextureGenerator* textureGenerator = new TextureGenerator(*object);
|
||||
for (const auto& layer : material.second) {
|
||||
for (const auto& mapItem : layer.maps) {
|
||||
const QImage* image = ImageForever::get(mapItem.imageId);
|
||||
if (nullptr == image)
|
||||
continue;
|
||||
for (const auto &partId: partIds) {
|
||||
for (const auto& partId : partIds) {
|
||||
if (dust3d::TextureType::BaseColor == mapItem.forWhat)
|
||||
textureGenerator->addPartColorMap(partId, image, layer.tileScale);
|
||||
else if (dust3d::TextureType::Normal == mapItem.forWhat)
|
||||
|
@ -102,7 +102,7 @@ void MaterialPreviewsGenerator::generate()
|
|||
}
|
||||
}
|
||||
textureGenerator->generate();
|
||||
ModelMesh *texturedResultMesh = textureGenerator->takeResultMesh();
|
||||
ModelMesh* texturedResultMesh = textureGenerator->takeResultMesh();
|
||||
if (nullptr != texturedResultMesh) {
|
||||
m_previews[material.first] = new ModelMesh(*texturedResultMesh);
|
||||
m_generatedMaterialIds.insert(material.first);
|
||||
|
|
|
@ -1,29 +1,29 @@
|
|||
#ifndef DUST3D_APPLICATION_MATERIAL_PREVIEWS_GENERATOR_H_
|
||||
#define DUST3D_APPLICATION_MATERIAL_PREVIEWS_GENERATOR_H_
|
||||
|
||||
#include "material_layer.h"
|
||||
#include "model_mesh.h"
|
||||
#include <QObject>
|
||||
#include <map>
|
||||
#include <vector>
|
||||
#include "model_mesh.h"
|
||||
#include "material_layer.h"
|
||||
|
||||
class MaterialPreviewsGenerator : public QObject
|
||||
{
|
||||
class MaterialPreviewsGenerator : public QObject {
|
||||
Q_OBJECT
|
||||
public:
|
||||
MaterialPreviewsGenerator();
|
||||
~MaterialPreviewsGenerator();
|
||||
void addMaterial(dust3d::Uuid materialId, const std::vector<MaterialLayer> &layers);
|
||||
const std::set<dust3d::Uuid> &generatedPreviewMaterialIds();
|
||||
ModelMesh *takePreview(dust3d::Uuid materialId);
|
||||
void addMaterial(dust3d::Uuid materialId, const std::vector<MaterialLayer>& layers);
|
||||
const std::set<dust3d::Uuid>& generatedPreviewMaterialIds();
|
||||
ModelMesh* takePreview(dust3d::Uuid materialId);
|
||||
void generate();
|
||||
signals:
|
||||
void finished();
|
||||
public slots:
|
||||
void process();
|
||||
|
||||
private:
|
||||
std::vector<std::pair<dust3d::Uuid, std::vector<MaterialLayer>>> m_materials;
|
||||
std::map<dust3d::Uuid, ModelMesh *> m_previews;
|
||||
std::map<dust3d::Uuid, ModelMesh*> m_previews;
|
||||
std::set<dust3d::Uuid> m_generatedMaterialIds;
|
||||
};
|
||||
|
||||
|
|
|
@ -1,10 +1,10 @@
|
|||
#include <QVBoxLayout>
|
||||
#include "material_widget.h"
|
||||
#include "document.h"
|
||||
#include <QVBoxLayout>
|
||||
|
||||
MaterialWidget::MaterialWidget(const Document *document, dust3d::Uuid materialId) :
|
||||
m_materialId(materialId),
|
||||
m_document(document)
|
||||
MaterialWidget::MaterialWidget(const Document* document, dust3d::Uuid materialId)
|
||||
: m_materialId(materialId)
|
||||
, m_document(document)
|
||||
{
|
||||
setObjectName("MaterialFrame");
|
||||
|
||||
|
@ -23,7 +23,7 @@ MaterialWidget::MaterialWidget(const Document *document, dust3d::Uuid materialId
|
|||
nameFont.setBold(false);
|
||||
m_nameLabel->setFont(nameFont);
|
||||
|
||||
QVBoxLayout *mainLayout = new QVBoxLayout;
|
||||
QVBoxLayout* mainLayout = new QVBoxLayout;
|
||||
mainLayout->setContentsMargins(0, 0, 0, 0);
|
||||
mainLayout->addStretch();
|
||||
mainLayout->addWidget(m_nameLabel);
|
||||
|
@ -36,7 +36,7 @@ MaterialWidget::MaterialWidget(const Document *document, dust3d::Uuid materialId
|
|||
connect(document, &Document::materialPreviewChanged, this, &MaterialWidget::updatePreview);
|
||||
}
|
||||
|
||||
void MaterialWidget::resizeEvent(QResizeEvent *event)
|
||||
void MaterialWidget::resizeEvent(QResizeEvent* event)
|
||||
{
|
||||
QWidget::resizeEvent(event);
|
||||
m_previewWidget->move((width() - Theme::materialPreviewImageSize) / 2, 0);
|
||||
|
@ -57,12 +57,12 @@ void MaterialWidget::updatePreview(dust3d::Uuid materialId)
|
|||
{
|
||||
if (materialId != m_materialId)
|
||||
return;
|
||||
const Material *material = m_document->findMaterial(m_materialId);
|
||||
const Material* material = m_document->findMaterial(m_materialId);
|
||||
if (!material) {
|
||||
qDebug() << "Material not found:" << m_materialId;
|
||||
return;
|
||||
}
|
||||
ModelMesh *previewMesh = material->takePreviewMesh();
|
||||
ModelMesh* previewMesh = material->takePreviewMesh();
|
||||
m_previewWidget->updateMesh(previewMesh);
|
||||
}
|
||||
|
||||
|
@ -70,7 +70,7 @@ void MaterialWidget::updateName(dust3d::Uuid materialId)
|
|||
{
|
||||
if (materialId != m_materialId)
|
||||
return;
|
||||
const Material *material = m_document->findMaterial(m_materialId);
|
||||
const Material* material = m_document->findMaterial(m_materialId);
|
||||
if (!material) {
|
||||
qDebug() << "Material not found:" << m_materialId;
|
||||
return;
|
||||
|
@ -86,12 +86,12 @@ void MaterialWidget::updateCheckedState(bool checked)
|
|||
setStyleSheet("#MaterialFrame {border: 1px solid transparent;}");
|
||||
}
|
||||
|
||||
ModelWidget *MaterialWidget::previewWidget()
|
||||
ModelWidget* MaterialWidget::previewWidget()
|
||||
{
|
||||
return m_previewWidget;
|
||||
}
|
||||
|
||||
void MaterialWidget::mouseDoubleClickEvent(QMouseEvent *event)
|
||||
void MaterialWidget::mouseDoubleClickEvent(QMouseEvent* event)
|
||||
{
|
||||
QFrame::mouseDoubleClickEvent(event);
|
||||
emit modifyMaterial(m_materialId);
|
||||
|
|
|
@ -1,36 +1,38 @@
|
|||
#ifndef DUST3D_APPLICATION_MATERIAL_WIDGET_H_
|
||||
#define DUST3D_APPLICATION_MATERIAL_WIDGET_H_
|
||||
|
||||
#include <QFrame>
|
||||
#include <QLabel>
|
||||
#include <QIcon>
|
||||
#include <QPushButton>
|
||||
#include "model_widget.h"
|
||||
#include <QFrame>
|
||||
#include <QIcon>
|
||||
#include <QLabel>
|
||||
#include <QPushButton>
|
||||
|
||||
class Document;
|
||||
|
||||
class MaterialWidget : public QFrame
|
||||
{
|
||||
class MaterialWidget : public QFrame {
|
||||
Q_OBJECT
|
||||
signals:
|
||||
void modifyMaterial(dust3d::Uuid materialId);
|
||||
|
||||
public:
|
||||
MaterialWidget(const Document *document, dust3d::Uuid materialId);
|
||||
MaterialWidget(const Document* document, dust3d::Uuid materialId);
|
||||
static int preferredHeight();
|
||||
ModelWidget *previewWidget();
|
||||
ModelWidget* previewWidget();
|
||||
|
||||
protected:
|
||||
void mouseDoubleClickEvent(QMouseEvent *event) override;
|
||||
void resizeEvent(QResizeEvent *event) override;
|
||||
void mouseDoubleClickEvent(QMouseEvent* event) override;
|
||||
void resizeEvent(QResizeEvent* event) override;
|
||||
public slots:
|
||||
void reload();
|
||||
void updatePreview(dust3d::Uuid materialId);
|
||||
void updateName(dust3d::Uuid materialId);
|
||||
void updateCheckedState(bool checked);
|
||||
|
||||
private:
|
||||
dust3d::Uuid m_materialId;
|
||||
const Document *m_document = nullptr;
|
||||
ModelWidget *m_previewWidget = nullptr;
|
||||
QLabel *m_nameLabel = nullptr;
|
||||
const Document* m_document = nullptr;
|
||||
ModelWidget* m_previewWidget = nullptr;
|
||||
QLabel* m_nameLabel = nullptr;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
@ -1,13 +1,13 @@
|
|||
|
||||
#include <dust3d/mesh/smooth_normal.h>
|
||||
#include <dust3d/mesh/trim_vertices.h>
|
||||
#include <QElapsedTimer>
|
||||
#include <QDebug>
|
||||
#include "mesh_generator.h"
|
||||
#include "cut_face_preview.h"
|
||||
#include <QDebug>
|
||||
#include <QElapsedTimer>
|
||||
#include <dust3d/mesh/smooth_normal.h>
|
||||
#include <dust3d/mesh/trim_vertices.h>
|
||||
|
||||
MeshGenerator::MeshGenerator(dust3d::Snapshot *snapshot) :
|
||||
dust3d::MeshGenerator(snapshot)
|
||||
MeshGenerator::MeshGenerator(dust3d::Snapshot* snapshot)
|
||||
: dust3d::MeshGenerator(snapshot)
|
||||
{
|
||||
}
|
||||
|
||||
|
@ -15,12 +15,12 @@ MeshGenerator::~MeshGenerator()
|
|||
{
|
||||
}
|
||||
|
||||
std::map<dust3d::Uuid, std::unique_ptr<ModelMesh>> *MeshGenerator::takeComponentPreviewMeshes()
|
||||
std::map<dust3d::Uuid, std::unique_ptr<ModelMesh>>* MeshGenerator::takeComponentPreviewMeshes()
|
||||
{
|
||||
return m_componentPreviewMeshes.release();
|
||||
}
|
||||
|
||||
MonochromeMesh *MeshGenerator::takeWireframeMesh()
|
||||
MonochromeMesh* MeshGenerator::takeWireframeMesh()
|
||||
{
|
||||
return m_wireframeMesh.release();
|
||||
}
|
||||
|
@ -36,22 +36,21 @@ void MeshGenerator::process()
|
|||
m_resultMesh = std::make_unique<ModelMesh>(*m_object);
|
||||
|
||||
m_componentPreviewMeshes = std::make_unique<std::map<dust3d::Uuid, std::unique_ptr<ModelMesh>>>();
|
||||
for (const auto &componentId: m_generatedPreviewComponentIds) {
|
||||
for (const auto& componentId : m_generatedPreviewComponentIds) {
|
||||
auto it = m_generatedComponentPreviews.find(componentId);
|
||||
if (it == m_generatedComponentPreviews.end())
|
||||
continue;
|
||||
dust3d::trimVertices(&it->second.vertices, true);
|
||||
for (auto &it: it->second.vertices) {
|
||||
for (auto& it : it->second.vertices) {
|
||||
it *= 2.0;
|
||||
}
|
||||
std::vector<dust3d::Vector3> previewTriangleNormals;
|
||||
previewTriangleNormals.reserve(it->second.triangles.size());
|
||||
for (const auto &face: it->second.triangles) {
|
||||
for (const auto& face : it->second.triangles) {
|
||||
previewTriangleNormals.emplace_back(dust3d::Vector3::normal(
|
||||
it->second.vertices[face[0]],
|
||||
it->second.vertices[face[1]],
|
||||
it->second.vertices[face[2]]
|
||||
));
|
||||
it->second.vertices[face[2]]));
|
||||
}
|
||||
std::vector<std::vector<dust3d::Vector3>> previewTriangleVertexNormals;
|
||||
dust3d::smoothNormal(it->second.vertices,
|
||||
|
@ -76,8 +75,7 @@ void MeshGenerator::process()
|
|||
emit finished();
|
||||
}
|
||||
|
||||
ModelMesh *MeshGenerator::takeResultMesh()
|
||||
ModelMesh* MeshGenerator::takeResultMesh()
|
||||
{
|
||||
return m_resultMesh.release();
|
||||
}
|
||||
|
||||
|
|
|
@ -1,26 +1,26 @@
|
|||
#ifndef DUST3D_APPLICATION_MESH_GENERATOR_H_
|
||||
#define DUST3D_APPLICATION_MESH_GENERATOR_H_
|
||||
|
||||
#include <memory>
|
||||
#include <QObject>
|
||||
#include <QImage>
|
||||
#include <dust3d/mesh/mesh_generator.h>
|
||||
#include "model_mesh.h"
|
||||
#include "monochrome_mesh.h"
|
||||
#include <QImage>
|
||||
#include <QObject>
|
||||
#include <dust3d/mesh/mesh_generator.h>
|
||||
#include <memory>
|
||||
|
||||
class MeshGenerator : public QObject, public dust3d::MeshGenerator
|
||||
{
|
||||
class MeshGenerator : public QObject, public dust3d::MeshGenerator {
|
||||
Q_OBJECT
|
||||
public:
|
||||
MeshGenerator(dust3d::Snapshot *snapshot);
|
||||
MeshGenerator(dust3d::Snapshot* snapshot);
|
||||
~MeshGenerator();
|
||||
ModelMesh *takeResultMesh();
|
||||
std::map<dust3d::Uuid, std::unique_ptr<ModelMesh>> *takeComponentPreviewMeshes();
|
||||
MonochromeMesh *takeWireframeMesh();
|
||||
ModelMesh* takeResultMesh();
|
||||
std::map<dust3d::Uuid, std::unique_ptr<ModelMesh>>* takeComponentPreviewMeshes();
|
||||
MonochromeMesh* takeWireframeMesh();
|
||||
public slots:
|
||||
void process();
|
||||
signals:
|
||||
void finished();
|
||||
|
||||
private:
|
||||
std::unique_ptr<ModelMesh> m_resultMesh;
|
||||
std::unique_ptr<std::map<dust3d::Uuid, std::unique_ptr<ModelMesh>>> m_componentPreviewMeshes;
|
||||
|
|
|
@ -1,10 +1,10 @@
|
|||
#include <QDebug>
|
||||
#include "mesh_preview_images_generator.h"
|
||||
#include "theme.h"
|
||||
#include <QDebug>
|
||||
|
||||
void MeshPreviewImagesGenerator::addInput(const dust3d::Uuid &inputId, std::unique_ptr<ModelMesh> previewMesh, bool useFrontView)
|
||||
void MeshPreviewImagesGenerator::addInput(const dust3d::Uuid& inputId, std::unique_ptr<ModelMesh> previewMesh, bool useFrontView)
|
||||
{
|
||||
m_previewInputMap.insert({inputId, PreviewInput {std::move(previewMesh), useFrontView}});
|
||||
m_previewInputMap.insert({ inputId, PreviewInput { std::move(previewMesh), useFrontView } });
|
||||
}
|
||||
|
||||
void MeshPreviewImagesGenerator::process()
|
||||
|
@ -14,7 +14,7 @@ void MeshPreviewImagesGenerator::process()
|
|||
emit finished();
|
||||
}
|
||||
|
||||
std::map<dust3d::Uuid, QImage> *MeshPreviewImagesGenerator::takeImages()
|
||||
std::map<dust3d::Uuid, QImage>* MeshPreviewImagesGenerator::takeImages()
|
||||
{
|
||||
return m_partImages.release();
|
||||
}
|
||||
|
@ -25,7 +25,7 @@ void MeshPreviewImagesGenerator::generate()
|
|||
|
||||
m_offscreenRender->setZRotation(0);
|
||||
m_offscreenRender->setEyePosition(QVector3D(0, 0, -4.0));
|
||||
for (auto &it: m_previewInputMap) {
|
||||
for (auto& it : m_previewInputMap) {
|
||||
if (it.second.useFrontView) {
|
||||
m_offscreenRender->setXRotation(0);
|
||||
m_offscreenRender->setYRotation(0);
|
||||
|
|
|
@ -1,24 +1,22 @@
|
|||
#ifndef DUST3D_APPLICATION_MESH_PREVIEW_IMAGES_GENERATOR_H_
|
||||
#define DUST3D_APPLICATION_MESH_PREVIEW_IMAGES_GENERATOR_H_
|
||||
|
||||
#include <QObject>
|
||||
#include <QImage>
|
||||
#include <memory>
|
||||
#include <map>
|
||||
#include <dust3d/base/uuid.h>
|
||||
#include "model_offscreen_render.h"
|
||||
#include <QImage>
|
||||
#include <QObject>
|
||||
#include <dust3d/base/uuid.h>
|
||||
#include <map>
|
||||
#include <memory>
|
||||
|
||||
class MeshPreviewImagesGenerator : public QObject
|
||||
{
|
||||
class MeshPreviewImagesGenerator : public QObject {
|
||||
Q_OBJECT
|
||||
public:
|
||||
MeshPreviewImagesGenerator(ModelOffscreenRender *modelOffscreenRender) :
|
||||
m_offscreenRender(modelOffscreenRender)
|
||||
MeshPreviewImagesGenerator(ModelOffscreenRender* modelOffscreenRender)
|
||||
: m_offscreenRender(modelOffscreenRender)
|
||||
{
|
||||
}
|
||||
|
||||
struct PreviewInput
|
||||
{
|
||||
struct PreviewInput {
|
||||
std::unique_ptr<ModelMesh> mesh;
|
||||
bool useFrontView = false;
|
||||
};
|
||||
|
@ -28,16 +26,17 @@ public:
|
|||
delete m_offscreenRender;
|
||||
}
|
||||
|
||||
void addInput(const dust3d::Uuid &inputId, std::unique_ptr<ModelMesh> previewMesh, bool useFrontView=false);
|
||||
void addInput(const dust3d::Uuid& inputId, std::unique_ptr<ModelMesh> previewMesh, bool useFrontView = false);
|
||||
void generate();
|
||||
std::map<dust3d::Uuid, QImage> *takeImages();
|
||||
std::map<dust3d::Uuid, QImage>* takeImages();
|
||||
signals:
|
||||
void finished();
|
||||
public slots:
|
||||
void process();
|
||||
|
||||
private:
|
||||
std::map<dust3d::Uuid, PreviewInput> m_previewInputMap;
|
||||
ModelOffscreenRender *m_offscreenRender = nullptr;
|
||||
ModelOffscreenRender* m_offscreenRender = nullptr;
|
||||
std::unique_ptr<std::map<dust3d::Uuid, QImage>> m_partImages;
|
||||
};
|
||||
|
||||
|
|
|
@ -1,9 +1,9 @@
|
|||
#include <QGuiApplication>
|
||||
#include <dust3d/uv/unwrap_uv.h>
|
||||
#include <dust3d/mesh/resolve_triangle_tangent.h>
|
||||
#include "mesh_result_post_processor.h"
|
||||
#include <QGuiApplication>
|
||||
#include <dust3d/mesh/resolve_triangle_tangent.h>
|
||||
#include <dust3d/uv/unwrap_uv.h>
|
||||
|
||||
MeshResultPostProcessor::MeshResultPostProcessor(const dust3d::Object &object)
|
||||
MeshResultPostProcessor::MeshResultPostProcessor(const dust3d::Object& object)
|
||||
{
|
||||
m_object = new dust3d::Object;
|
||||
*m_object = object;
|
||||
|
@ -14,9 +14,9 @@ MeshResultPostProcessor::~MeshResultPostProcessor()
|
|||
delete m_object;
|
||||
}
|
||||
|
||||
dust3d::Object *MeshResultPostProcessor::takePostProcessedObject()
|
||||
dust3d::Object* MeshResultPostProcessor::takePostProcessedObject()
|
||||
{
|
||||
dust3d::Object *object = m_object;
|
||||
dust3d::Object* object = m_object;
|
||||
m_object = nullptr;
|
||||
return object;
|
||||
}
|
||||
|
|
|
@ -4,20 +4,20 @@
|
|||
#include <QObject>
|
||||
#include <dust3d/base/object.h>
|
||||
|
||||
class MeshResultPostProcessor : public QObject
|
||||
{
|
||||
class MeshResultPostProcessor : public QObject {
|
||||
Q_OBJECT
|
||||
public:
|
||||
MeshResultPostProcessor(const dust3d::Object &object);
|
||||
MeshResultPostProcessor(const dust3d::Object& object);
|
||||
~MeshResultPostProcessor();
|
||||
dust3d::Object *takePostProcessedObject();
|
||||
dust3d::Object* takePostProcessedObject();
|
||||
void poseProcess();
|
||||
signals:
|
||||
void finished();
|
||||
public slots:
|
||||
void process();
|
||||
|
||||
private:
|
||||
dust3d::Object *m_object = nullptr;
|
||||
dust3d::Object* m_object = nullptr;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
@ -1,20 +1,19 @@
|
|||
#include <assert.h>
|
||||
#include <QTextStream>
|
||||
#include <QFile>
|
||||
#include <cmath>
|
||||
#include "model_mesh.h"
|
||||
#include "version.h"
|
||||
#include <QFile>
|
||||
#include <QTextStream>
|
||||
#include <assert.h>
|
||||
#include <cmath>
|
||||
|
||||
float ModelMesh::m_defaultMetalness = 0.0;
|
||||
float ModelMesh::m_defaultRoughness = 1.0;
|
||||
|
||||
ModelMesh::ModelMesh(const ModelMesh &mesh) :
|
||||
m_triangleVertices(nullptr),
|
||||
m_triangleVertexCount(0),
|
||||
m_textureImage(nullptr)
|
||||
ModelMesh::ModelMesh(const ModelMesh& mesh)
|
||||
: m_triangleVertices(nullptr)
|
||||
, m_triangleVertexCount(0)
|
||||
, m_textureImage(nullptr)
|
||||
{
|
||||
if (nullptr != mesh.m_triangleVertices &&
|
||||
mesh.m_triangleVertexCount > 0) {
|
||||
if (nullptr != mesh.m_triangleVertices && mesh.m_triangleVertexCount > 0) {
|
||||
this->m_triangleVertices = new ModelOpenGLVertex[mesh.m_triangleVertexCount];
|
||||
this->m_triangleVertexCount = mesh.m_triangleVertexCount;
|
||||
for (int i = 0; i < mesh.m_triangleVertexCount; i++)
|
||||
|
@ -54,27 +53,27 @@ void ModelMesh::removeColor()
|
|||
this->m_hasAmbientOcclusionInImage = false;
|
||||
|
||||
for (int i = 0; i < this->m_triangleVertexCount; ++i) {
|
||||
auto &vertex = this->m_triangleVertices[i];
|
||||
auto& vertex = this->m_triangleVertices[i];
|
||||
vertex.colorR = 1.0;
|
||||
vertex.colorG = 1.0;
|
||||
vertex.colorB = 1.0;
|
||||
}
|
||||
}
|
||||
|
||||
ModelMesh::ModelMesh(ModelOpenGLVertex *triangleVertices, int vertexNum) :
|
||||
m_triangleVertices(triangleVertices),
|
||||
m_triangleVertexCount(vertexNum),
|
||||
m_textureImage(nullptr)
|
||||
ModelMesh::ModelMesh(ModelOpenGLVertex* triangleVertices, int vertexNum)
|
||||
: m_triangleVertices(triangleVertices)
|
||||
, m_triangleVertexCount(vertexNum)
|
||||
, m_textureImage(nullptr)
|
||||
{
|
||||
}
|
||||
|
||||
ModelMesh::ModelMesh(const std::vector<dust3d::Vector3> &vertices,
|
||||
const std::vector<std::vector<size_t>> &triangles,
|
||||
const std::vector<std::vector<dust3d::Vector3>> &triangleVertexNormals,
|
||||
const dust3d::Color &color,
|
||||
ModelMesh::ModelMesh(const std::vector<dust3d::Vector3>& vertices,
|
||||
const std::vector<std::vector<size_t>>& triangles,
|
||||
const std::vector<std::vector<dust3d::Vector3>>& triangleVertexNormals,
|
||||
const dust3d::Color& color,
|
||||
float metalness,
|
||||
float roughness,
|
||||
const std::vector<std::tuple<dust3d::Color, float/*metalness*/, float/*roughness*/>> *vertexProperties)
|
||||
const std::vector<std::tuple<dust3d::Color, float /*metalness*/, float /*roughness*/>>* vertexProperties)
|
||||
{
|
||||
m_triangleVertexCount = (int)triangles.size() * 3;
|
||||
m_triangleVertices = new ModelOpenGLVertex[m_triangleVertexCount];
|
||||
|
@ -82,9 +81,9 @@ ModelMesh::ModelMesh(const std::vector<dust3d::Vector3> &vertices,
|
|||
for (size_t i = 0; i < triangles.size(); ++i) {
|
||||
for (auto j = 0; j < 3; j++) {
|
||||
int vertexIndex = (int)triangles[i][j];
|
||||
const dust3d::Vector3 *srcVert = &vertices[vertexIndex];
|
||||
const dust3d::Vector3 *srcNormal = &(triangleVertexNormals)[i][j];
|
||||
ModelOpenGLVertex *dest = &m_triangleVertices[destIndex];
|
||||
const dust3d::Vector3* srcVert = &vertices[vertexIndex];
|
||||
const dust3d::Vector3* srcNormal = &(triangleVertexNormals)[i][j];
|
||||
ModelOpenGLVertex* dest = &m_triangleVertices[destIndex];
|
||||
dest->posX = srcVert->x();
|
||||
dest->posY = srcVert->y();
|
||||
dest->posZ = srcVert->z();
|
||||
|
@ -101,7 +100,7 @@ ModelMesh::ModelMesh(const std::vector<dust3d::Vector3> &vertices,
|
|||
dest->metalness = metalness;
|
||||
dest->roughness = roughness;
|
||||
} else {
|
||||
const auto &property = (*vertexProperties)[vertexIndex];
|
||||
const auto& property = (*vertexProperties)[vertexIndex];
|
||||
dest->colorR = std::get<0>(property).r();
|
||||
dest->colorG = std::get<0>(property).g();
|
||||
dest->colorB = std::get<0>(property).b();
|
||||
|
@ -117,19 +116,19 @@ ModelMesh::ModelMesh(const std::vector<dust3d::Vector3> &vertices,
|
|||
}
|
||||
}
|
||||
|
||||
ModelMesh::ModelMesh(dust3d::Object &object) :
|
||||
m_triangleVertices(nullptr),
|
||||
m_triangleVertexCount(0),
|
||||
m_textureImage(nullptr)
|
||||
ModelMesh::ModelMesh(dust3d::Object& object)
|
||||
: m_triangleVertices(nullptr)
|
||||
, m_triangleVertexCount(0)
|
||||
, m_textureImage(nullptr)
|
||||
{
|
||||
m_meshId = object.meshId;
|
||||
m_vertices = object.vertices;
|
||||
m_faces = object.triangleAndQuads;
|
||||
|
||||
std::map<std::pair<dust3d::Uuid, dust3d::Uuid>, const dust3d::ObjectNode *> nodeMap;
|
||||
std::map<std::pair<dust3d::Uuid, dust3d::Uuid>, const dust3d::ObjectNode*> nodeMap;
|
||||
for (size_t i = 0; i < object.nodes.size(); ++i) {
|
||||
const auto &node = object.nodes[i];
|
||||
nodeMap.insert({{node.partId, node.nodeId}, &node});
|
||||
const auto& node = object.nodes[i];
|
||||
nodeMap.insert({ { node.partId, node.nodeId }, &node });
|
||||
}
|
||||
|
||||
m_triangleVertexCount = (int)object.triangles.size() * 3;
|
||||
|
@ -142,20 +141,20 @@ ModelMesh::ModelMesh(dust3d::Object &object) :
|
|||
const dust3d::Vector2 defaultUv = dust3d::Vector2(0, 0);
|
||||
const dust3d::Vector3 defaultTangent = dust3d::Vector3(0, 0, 0);
|
||||
for (size_t i = 0; i < object.triangles.size(); ++i) {
|
||||
const auto &triangleColor = &object.triangleColors[i];
|
||||
const auto& triangleColor = &object.triangleColors[i];
|
||||
for (auto j = 0; j < 3; j++) {
|
||||
int vertexIndex = (int)object.triangles[i][j];
|
||||
const dust3d::Vector3 *srcVert = &object.vertices[vertexIndex];
|
||||
const dust3d::Vector3 *srcNormal = &defaultNormal;
|
||||
const dust3d::Vector3* srcVert = &object.vertices[vertexIndex];
|
||||
const dust3d::Vector3* srcNormal = &defaultNormal;
|
||||
if (triangleVertexNormals)
|
||||
srcNormal = &(*triangleVertexNormals)[i][j];
|
||||
const dust3d::Vector2 *srcUv = &defaultUv;
|
||||
const dust3d::Vector2* srcUv = &defaultUv;
|
||||
if (triangleVertexUvs)
|
||||
srcUv = &(*triangleVertexUvs)[i][j];
|
||||
const dust3d::Vector3 *srcTangent = &defaultTangent;
|
||||
const dust3d::Vector3* srcTangent = &defaultTangent;
|
||||
if (triangleTangents)
|
||||
srcTangent = &(*triangleTangents)[i];
|
||||
ModelOpenGLVertex *dest = &m_triangleVertices[destIndex];
|
||||
ModelOpenGLVertex* dest = &m_triangleVertices[destIndex];
|
||||
dest->colorR = triangleColor->r();
|
||||
dest->colorG = triangleColor->g();
|
||||
dest->colorB = triangleColor->b();
|
||||
|
@ -184,10 +183,10 @@ ModelMesh::ModelMesh(dust3d::Object &object) :
|
|||
}
|
||||
}
|
||||
|
||||
ModelMesh::ModelMesh() :
|
||||
m_triangleVertices(nullptr),
|
||||
m_triangleVertexCount(0),
|
||||
m_textureImage(nullptr)
|
||||
ModelMesh::ModelMesh()
|
||||
: m_triangleVertices(nullptr)
|
||||
, m_triangleVertexCount(0)
|
||||
, m_textureImage(nullptr)
|
||||
{
|
||||
}
|
||||
|
||||
|
@ -200,22 +199,22 @@ ModelMesh::~ModelMesh()
|
|||
delete m_metalnessRoughnessAmbientOcclusionMapImage;
|
||||
}
|
||||
|
||||
const std::vector<dust3d::Vector3> &ModelMesh::vertices()
|
||||
const std::vector<dust3d::Vector3>& ModelMesh::vertices()
|
||||
{
|
||||
return m_vertices;
|
||||
}
|
||||
|
||||
const std::vector<std::vector<size_t>> &ModelMesh::faces()
|
||||
const std::vector<std::vector<size_t>>& ModelMesh::faces()
|
||||
{
|
||||
return m_faces;
|
||||
}
|
||||
|
||||
const std::vector<dust3d::Vector3> &ModelMesh::triangulatedVertices()
|
||||
const std::vector<dust3d::Vector3>& ModelMesh::triangulatedVertices()
|
||||
{
|
||||
return m_triangulatedVertices;
|
||||
}
|
||||
|
||||
ModelOpenGLVertex *ModelMesh::triangleVertices()
|
||||
ModelOpenGLVertex* ModelMesh::triangleVertices()
|
||||
{
|
||||
return m_triangleVertices;
|
||||
}
|
||||
|
@ -225,53 +224,53 @@ int ModelMesh::triangleVertexCount()
|
|||
return m_triangleVertexCount;
|
||||
}
|
||||
|
||||
void ModelMesh::setTextureImage(QImage *textureImage)
|
||||
void ModelMesh::setTextureImage(QImage* textureImage)
|
||||
{
|
||||
m_textureImage = textureImage;
|
||||
}
|
||||
|
||||
const QImage *ModelMesh::textureImage()
|
||||
const QImage* ModelMesh::textureImage()
|
||||
{
|
||||
return m_textureImage;
|
||||
}
|
||||
|
||||
QImage *ModelMesh::takeTextureImage()
|
||||
QImage* ModelMesh::takeTextureImage()
|
||||
{
|
||||
auto image = m_textureImage;
|
||||
m_textureImage = nullptr;
|
||||
return image;
|
||||
}
|
||||
|
||||
void ModelMesh::setNormalMapImage(QImage *normalMapImage)
|
||||
void ModelMesh::setNormalMapImage(QImage* normalMapImage)
|
||||
{
|
||||
m_normalMapImage = normalMapImage;
|
||||
}
|
||||
|
||||
const QImage *ModelMesh::normalMapImage()
|
||||
const QImage* ModelMesh::normalMapImage()
|
||||
{
|
||||
return m_normalMapImage;
|
||||
}
|
||||
|
||||
QImage *ModelMesh::takeNormalMapImage()
|
||||
QImage* ModelMesh::takeNormalMapImage()
|
||||
{
|
||||
auto image = m_normalMapImage;
|
||||
m_normalMapImage = nullptr;
|
||||
return image;
|
||||
}
|
||||
|
||||
const QImage *ModelMesh::metalnessRoughnessAmbientOcclusionMapImage()
|
||||
const QImage* ModelMesh::metalnessRoughnessAmbientOcclusionMapImage()
|
||||
{
|
||||
return m_metalnessRoughnessAmbientOcclusionMapImage;
|
||||
}
|
||||
|
||||
QImage *ModelMesh::takeMetalnessRoughnessAmbientOcclusionMapImage()
|
||||
QImage* ModelMesh::takeMetalnessRoughnessAmbientOcclusionMapImage()
|
||||
{
|
||||
auto image = m_metalnessRoughnessAmbientOcclusionMapImage;
|
||||
m_metalnessRoughnessAmbientOcclusionMapImage = nullptr;
|
||||
return image;
|
||||
}
|
||||
|
||||
void ModelMesh::setMetalnessRoughnessAmbientOcclusionMapImage(QImage *image)
|
||||
void ModelMesh::setMetalnessRoughnessAmbientOcclusionMapImage(QImage* image)
|
||||
{
|
||||
m_metalnessRoughnessAmbientOcclusionMapImage = image;
|
||||
}
|
||||
|
@ -306,24 +305,24 @@ void ModelMesh::setHasAmbientOcclusionInImage(bool hasInImage)
|
|||
m_hasAmbientOcclusionInImage = hasInImage;
|
||||
}
|
||||
|
||||
void ModelMesh::exportAsObj(QTextStream *textStream)
|
||||
void ModelMesh::exportAsObj(QTextStream* textStream)
|
||||
{
|
||||
auto &stream = *textStream;
|
||||
auto& stream = *textStream;
|
||||
stream << "# " << APP_NAME << " " << APP_HUMAN_VER << endl;
|
||||
stream << "# " << APP_HOMEPAGE_URL << endl;
|
||||
for (std::vector<dust3d::Vector3>::const_iterator it = vertices().begin() ; it != vertices().end(); ++it) {
|
||||
for (std::vector<dust3d::Vector3>::const_iterator it = vertices().begin(); it != vertices().end(); ++it) {
|
||||
stream << "v " << QString::number((*it).x()) << " " << QString::number((*it).y()) << " " << QString::number((*it).z()) << endl;
|
||||
}
|
||||
for (std::vector<std::vector<size_t>>::const_iterator it = faces().begin() ; it != faces().end(); ++it) {
|
||||
for (std::vector<std::vector<size_t>>::const_iterator it = faces().begin(); it != faces().end(); ++it) {
|
||||
stream << "f";
|
||||
for (std::vector<size_t>::const_iterator subIt = (*it).begin() ; subIt != (*it).end(); ++subIt) {
|
||||
for (std::vector<size_t>::const_iterator subIt = (*it).begin(); subIt != (*it).end(); ++subIt) {
|
||||
stream << " " << QString::number((1 + *subIt));
|
||||
}
|
||||
stream << endl;
|
||||
}
|
||||
}
|
||||
|
||||
void ModelMesh::exportAsObj(const QString &filename)
|
||||
void ModelMesh::exportAsObj(const QString& filename)
|
||||
{
|
||||
QFile file(filename);
|
||||
if (file.open(QIODevice::WriteOnly)) {
|
||||
|
@ -332,7 +331,7 @@ void ModelMesh::exportAsObj(const QString &filename)
|
|||
}
|
||||
}
|
||||
|
||||
void ModelMesh::updateTriangleVertices(ModelOpenGLVertex *triangleVertices, int triangleVertexCount)
|
||||
void ModelMesh::updateTriangleVertices(ModelOpenGLVertex* triangleVertices, int triangleVertexCount)
|
||||
{
|
||||
delete[] m_triangleVertices;
|
||||
m_triangleVertices = 0;
|
||||
|
|
|
@ -1,44 +1,43 @@
|
|||
#ifndef DUST3D_APPLICATION_MODEL_MESH_H_
|
||||
#define DUST3D_APPLICATION_MODEL_MESH_H_
|
||||
|
||||
#include <QObject>
|
||||
#include <vector>
|
||||
#include "model_opengl_vertex.h"
|
||||
#include <QImage>
|
||||
#include <QObject>
|
||||
#include <QTextStream>
|
||||
#include <dust3d/base/vector3.h>
|
||||
#include <dust3d/base/color.h>
|
||||
#include <dust3d/base/object.h>
|
||||
#include "model_opengl_vertex.h"
|
||||
#include <dust3d/base/vector3.h>
|
||||
#include <vector>
|
||||
|
||||
class ModelMesh
|
||||
{
|
||||
class ModelMesh {
|
||||
public:
|
||||
ModelMesh(const std::vector<dust3d::Vector3> &vertices,
|
||||
const std::vector<std::vector<size_t>> &triangles,
|
||||
const std::vector<std::vector<dust3d::Vector3>> &triangleVertexNormals,
|
||||
const dust3d::Color &color=dust3d::Color::createWhite(),
|
||||
float metalness=0.0,
|
||||
float roughness=1.0,
|
||||
const std::vector<std::tuple<dust3d::Color, float/*metalness*/, float/*roughness*/>> *vertexProperties=nullptr);
|
||||
ModelMesh(dust3d::Object &object);
|
||||
ModelMesh(ModelOpenGLVertex *triangleVertices, int vertexNum);
|
||||
ModelMesh(const ModelMesh &mesh);
|
||||
ModelMesh(const std::vector<dust3d::Vector3>& vertices,
|
||||
const std::vector<std::vector<size_t>>& triangles,
|
||||
const std::vector<std::vector<dust3d::Vector3>>& triangleVertexNormals,
|
||||
const dust3d::Color& color = dust3d::Color::createWhite(),
|
||||
float metalness = 0.0,
|
||||
float roughness = 1.0,
|
||||
const std::vector<std::tuple<dust3d::Color, float /*metalness*/, float /*roughness*/>>* vertexProperties = nullptr);
|
||||
ModelMesh(dust3d::Object& object);
|
||||
ModelMesh(ModelOpenGLVertex* triangleVertices, int vertexNum);
|
||||
ModelMesh(const ModelMesh& mesh);
|
||||
ModelMesh();
|
||||
~ModelMesh();
|
||||
ModelOpenGLVertex *triangleVertices();
|
||||
ModelOpenGLVertex* triangleVertices();
|
||||
int triangleVertexCount();
|
||||
const std::vector<dust3d::Vector3> &vertices();
|
||||
const std::vector<std::vector<size_t>> &faces();
|
||||
const std::vector<dust3d::Vector3> &triangulatedVertices();
|
||||
void setTextureImage(QImage *textureImage);
|
||||
const QImage *textureImage();
|
||||
QImage *takeTextureImage();
|
||||
void setNormalMapImage(QImage *normalMapImage);
|
||||
const QImage *normalMapImage();
|
||||
QImage *takeNormalMapImage();
|
||||
const QImage *metalnessRoughnessAmbientOcclusionMapImage();
|
||||
QImage *takeMetalnessRoughnessAmbientOcclusionMapImage();
|
||||
void setMetalnessRoughnessAmbientOcclusionMapImage(QImage *image);
|
||||
const std::vector<dust3d::Vector3>& vertices();
|
||||
const std::vector<std::vector<size_t>>& faces();
|
||||
const std::vector<dust3d::Vector3>& triangulatedVertices();
|
||||
void setTextureImage(QImage* textureImage);
|
||||
const QImage* textureImage();
|
||||
QImage* takeTextureImage();
|
||||
void setNormalMapImage(QImage* normalMapImage);
|
||||
const QImage* normalMapImage();
|
||||
QImage* takeNormalMapImage();
|
||||
const QImage* metalnessRoughnessAmbientOcclusionMapImage();
|
||||
QImage* takeMetalnessRoughnessAmbientOcclusionMapImage();
|
||||
void setMetalnessRoughnessAmbientOcclusionMapImage(QImage* image);
|
||||
bool hasMetalnessInImage();
|
||||
void setHasMetalnessInImage(bool hasInImage);
|
||||
bool hasRoughnessInImage();
|
||||
|
@ -47,21 +46,22 @@ public:
|
|||
void setHasAmbientOcclusionInImage(bool hasInImage);
|
||||
static float m_defaultMetalness;
|
||||
static float m_defaultRoughness;
|
||||
void exportAsObj(const QString &filename);
|
||||
void exportAsObj(QTextStream *textStream);
|
||||
void updateTriangleVertices(ModelOpenGLVertex *triangleVertices, int triangleVertexCount);
|
||||
void exportAsObj(const QString& filename);
|
||||
void exportAsObj(QTextStream* textStream);
|
||||
void updateTriangleVertices(ModelOpenGLVertex* triangleVertices, int triangleVertexCount);
|
||||
quint64 meshId() const;
|
||||
void setMeshId(quint64 id);
|
||||
void removeColor();
|
||||
|
||||
private:
|
||||
ModelOpenGLVertex *m_triangleVertices = nullptr;
|
||||
ModelOpenGLVertex* m_triangleVertices = nullptr;
|
||||
int m_triangleVertexCount = 0;
|
||||
std::vector<dust3d::Vector3> m_vertices;
|
||||
std::vector<std::vector<size_t>> m_faces;
|
||||
std::vector<dust3d::Vector3> m_triangulatedVertices;
|
||||
QImage *m_textureImage = nullptr;
|
||||
QImage *m_normalMapImage = nullptr;
|
||||
QImage *m_metalnessRoughnessAmbientOcclusionMapImage = nullptr;
|
||||
QImage* m_textureImage = nullptr;
|
||||
QImage* m_normalMapImage = nullptr;
|
||||
QImage* m_metalnessRoughnessAmbientOcclusionMapImage = nullptr;
|
||||
bool m_hasMetalnessInImage = false;
|
||||
bool m_hasRoughnessInImage = false;
|
||||
bool m_hasAmbientOcclusionInImage = false;
|
||||
|
|
|
@ -2,10 +2,10 @@
|
|||
#include "model_opengl_object.h"
|
||||
#include "model_opengl_program.h"
|
||||
|
||||
ModelOffscreenRender::ModelOffscreenRender(const QSurfaceFormat &format, QScreen *targetScreen):
|
||||
QOffscreenSurface(targetScreen),
|
||||
m_context(nullptr),
|
||||
m_mesh(nullptr)
|
||||
ModelOffscreenRender::ModelOffscreenRender(const QSurfaceFormat& format, QScreen* targetScreen)
|
||||
: QOffscreenSurface(targetScreen)
|
||||
, m_context(nullptr)
|
||||
, m_mesh(nullptr)
|
||||
{
|
||||
setFormat(format);
|
||||
create();
|
||||
|
@ -37,28 +37,28 @@ void ModelOffscreenRender::setZRotation(int angle)
|
|||
m_zRot = angle;
|
||||
}
|
||||
|
||||
void ModelOffscreenRender::setEyePosition(const QVector3D &eyePosition)
|
||||
void ModelOffscreenRender::setEyePosition(const QVector3D& eyePosition)
|
||||
{
|
||||
m_eyePosition = eyePosition;
|
||||
}
|
||||
|
||||
void ModelOffscreenRender::setMoveToPosition(const QVector3D &moveToPosition)
|
||||
void ModelOffscreenRender::setMoveToPosition(const QVector3D& moveToPosition)
|
||||
{
|
||||
m_moveToPosition = moveToPosition;
|
||||
}
|
||||
|
||||
void ModelOffscreenRender::setRenderThread(QThread *thread)
|
||||
void ModelOffscreenRender::setRenderThread(QThread* thread)
|
||||
{
|
||||
moveToThread(thread);
|
||||
}
|
||||
|
||||
void ModelOffscreenRender::updateMesh(ModelMesh *mesh)
|
||||
void ModelOffscreenRender::updateMesh(ModelMesh* mesh)
|
||||
{
|
||||
delete m_mesh;
|
||||
m_mesh = mesh;
|
||||
}
|
||||
|
||||
QImage ModelOffscreenRender::toImage(const QSize &size)
|
||||
QImage ModelOffscreenRender::toImage(const QSize& size)
|
||||
{
|
||||
QImage image;
|
||||
|
||||
|
@ -105,7 +105,7 @@ QImage ModelOffscreenRender::toImage(const QSize &size)
|
|||
m_renderFbo = new QOpenGLFramebufferObject(size, format);
|
||||
m_renderFbo->bind();
|
||||
|
||||
QOpenGLFunctions *f = m_context->functions();
|
||||
QOpenGLFunctions* f = m_context->functions();
|
||||
f->glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
|
||||
f->glEnable(GL_BLEND);
|
||||
f->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
|
||||
|
|
|
@ -1,34 +1,34 @@
|
|||
#ifndef DUST3D_APPLICATION_MODEL_OFFSCREEN_RENDER_H_
|
||||
#define DUST3D_APPLICATION_MODEL_OFFSCREEN_RENDER_H_
|
||||
|
||||
#include "model_mesh.h"
|
||||
#include <QOffscreenSurface>
|
||||
#include <QOpenGLFramebufferObject>
|
||||
#include <QSurfaceFormat>
|
||||
#include <QVector3D>
|
||||
#include "model_mesh.h"
|
||||
|
||||
class ModelOffscreenRender: public QOffscreenSurface
|
||||
{
|
||||
class ModelOffscreenRender : public QOffscreenSurface {
|
||||
public:
|
||||
ModelOffscreenRender(const QSurfaceFormat &format, QScreen *targetScreen=Q_NULLPTR);
|
||||
ModelOffscreenRender(const QSurfaceFormat& format, QScreen* targetScreen = Q_NULLPTR);
|
||||
~ModelOffscreenRender();
|
||||
void setXRotation(int angle);
|
||||
void setYRotation(int angle);
|
||||
void setZRotation(int angle);
|
||||
void setEyePosition(const QVector3D &eyePosition);
|
||||
void setMoveToPosition(const QVector3D &moveToPosition);
|
||||
void setRenderThread(QThread *thread);
|
||||
void updateMesh(ModelMesh *mesh);
|
||||
QImage toImage(const QSize &size);
|
||||
void setEyePosition(const QVector3D& eyePosition);
|
||||
void setMoveToPosition(const QVector3D& moveToPosition);
|
||||
void setRenderThread(QThread* thread);
|
||||
void updateMesh(ModelMesh* mesh);
|
||||
QImage toImage(const QSize& size);
|
||||
|
||||
private:
|
||||
int m_xRot = 0;
|
||||
int m_yRot = 0;
|
||||
int m_zRot = 0;
|
||||
QVector3D m_eyePosition;
|
||||
QVector3D m_moveToPosition;
|
||||
QOpenGLContext *m_context = nullptr;
|
||||
QOpenGLFramebufferObject *m_renderFbo = nullptr;
|
||||
ModelMesh *m_mesh = nullptr;
|
||||
QOpenGLContext* m_context = nullptr;
|
||||
QOpenGLFramebufferObject* m_renderFbo = nullptr;
|
||||
ModelMesh* m_mesh = nullptr;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
#include <dust3d/base/debug.h>
|
||||
#include <QOpenGLFunctions>
|
||||
#include <QOpenGLContext>
|
||||
#include "model_opengl_object.h"
|
||||
#include <QOpenGLContext>
|
||||
#include <QOpenGLFunctions>
|
||||
#include <dust3d/base/debug.h>
|
||||
|
||||
void ModelOpenGLObject::update(std::unique_ptr<ModelMesh> mesh)
|
||||
{
|
||||
|
@ -15,7 +15,7 @@ void ModelOpenGLObject::draw()
|
|||
copyMeshToOpenGL();
|
||||
if (0 == m_meshTriangleVertexCount)
|
||||
return;
|
||||
QOpenGLFunctions *f = QOpenGLContext::currentContext()->functions();
|
||||
QOpenGLFunctions* f = QOpenGLContext::currentContext()->functions();
|
||||
QOpenGLVertexArrayObject::Binder binder(&m_vertexArrayObject);
|
||||
f->glDrawArrays(GL_TRIANGLES, 0, m_meshTriangleVertexCount);
|
||||
}
|
||||
|
@ -43,7 +43,7 @@ void ModelOpenGLObject::copyMeshToOpenGL()
|
|||
m_buffer.bind();
|
||||
m_buffer.allocate(mesh->triangleVertices(), mesh->triangleVertexCount() * sizeof(ModelOpenGLVertex));
|
||||
m_meshTriangleVertexCount = mesh->triangleVertexCount();
|
||||
QOpenGLFunctions *f = QOpenGLContext::currentContext()->functions();
|
||||
QOpenGLFunctions* f = QOpenGLContext::currentContext()->functions();
|
||||
f->glEnableVertexAttribArray(0);
|
||||
f->glEnableVertexAttribArray(1);
|
||||
f->glEnableVertexAttribArray(2);
|
||||
|
@ -53,13 +53,13 @@ void ModelOpenGLObject::copyMeshToOpenGL()
|
|||
f->glEnableVertexAttribArray(6);
|
||||
f->glEnableVertexAttribArray(7);
|
||||
f->glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, sizeof(ModelOpenGLVertex), 0);
|
||||
f->glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, sizeof(ModelOpenGLVertex), reinterpret_cast<void *>(3 * sizeof(GLfloat)));
|
||||
f->glVertexAttribPointer(2, 3, GL_FLOAT, GL_FALSE, sizeof(ModelOpenGLVertex), reinterpret_cast<void *>(6 * sizeof(GLfloat)));
|
||||
f->glVertexAttribPointer(3, 2, GL_FLOAT, GL_FALSE, sizeof(ModelOpenGLVertex), reinterpret_cast<void *>(9 * sizeof(GLfloat)));
|
||||
f->glVertexAttribPointer(4, 1, GL_FLOAT, GL_FALSE, sizeof(ModelOpenGLVertex), reinterpret_cast<void *>(11 * sizeof(GLfloat)));
|
||||
f->glVertexAttribPointer(5, 1, GL_FLOAT, GL_FALSE, sizeof(ModelOpenGLVertex), reinterpret_cast<void *>(12 * sizeof(GLfloat)));
|
||||
f->glVertexAttribPointer(6, 3, GL_FLOAT, GL_FALSE, sizeof(ModelOpenGLVertex), reinterpret_cast<void *>(13 * sizeof(GLfloat)));
|
||||
f->glVertexAttribPointer(7, 1, GL_FLOAT, GL_FALSE, sizeof(ModelOpenGLVertex), reinterpret_cast<void *>(16 * sizeof(GLfloat)));
|
||||
f->glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, sizeof(ModelOpenGLVertex), reinterpret_cast<void*>(3 * sizeof(GLfloat)));
|
||||
f->glVertexAttribPointer(2, 3, GL_FLOAT, GL_FALSE, sizeof(ModelOpenGLVertex), reinterpret_cast<void*>(6 * sizeof(GLfloat)));
|
||||
f->glVertexAttribPointer(3, 2, GL_FLOAT, GL_FALSE, sizeof(ModelOpenGLVertex), reinterpret_cast<void*>(9 * sizeof(GLfloat)));
|
||||
f->glVertexAttribPointer(4, 1, GL_FLOAT, GL_FALSE, sizeof(ModelOpenGLVertex), reinterpret_cast<void*>(11 * sizeof(GLfloat)));
|
||||
f->glVertexAttribPointer(5, 1, GL_FLOAT, GL_FALSE, sizeof(ModelOpenGLVertex), reinterpret_cast<void*>(12 * sizeof(GLfloat)));
|
||||
f->glVertexAttribPointer(6, 3, GL_FLOAT, GL_FALSE, sizeof(ModelOpenGLVertex), reinterpret_cast<void*>(13 * sizeof(GLfloat)));
|
||||
f->glVertexAttribPointer(7, 1, GL_FLOAT, GL_FALSE, sizeof(ModelOpenGLVertex), reinterpret_cast<void*>(16 * sizeof(GLfloat)));
|
||||
m_buffer.release();
|
||||
}
|
||||
}
|
|
@ -1,17 +1,17 @@
|
|||
#ifndef DUST3D_APPLICATION_MODEL_OPENGL_OBJECT_H_
|
||||
#define DUST3D_APPLICATION_MODEL_OPENGL_OBJECT_H_
|
||||
|
||||
#include <memory>
|
||||
#include <QMutex>
|
||||
#include <QOpenGLVertexArrayObject>
|
||||
#include <QOpenGLBuffer>
|
||||
#include "model_mesh.h"
|
||||
#include <QMutex>
|
||||
#include <QOpenGLBuffer>
|
||||
#include <QOpenGLVertexArrayObject>
|
||||
#include <memory>
|
||||
|
||||
class ModelOpenGLObject
|
||||
{
|
||||
class ModelOpenGLObject {
|
||||
public:
|
||||
void update(std::unique_ptr<ModelMesh> mesh);
|
||||
void draw();
|
||||
|
||||
private:
|
||||
void copyMeshToOpenGL();
|
||||
QOpenGLVertexArrayObject m_vertexArrayObject;
|
||||
|
|
|
@ -1,11 +1,11 @@
|
|||
#include <QOpenGLFunctions>
|
||||
#include <QFile>
|
||||
#include <QMutexLocker>
|
||||
#include <dust3d/base/debug.h>
|
||||
#include "model_opengl_program.h"
|
||||
#include "dds_file.h"
|
||||
#include <QFile>
|
||||
#include <QMutexLocker>
|
||||
#include <QOpenGLFunctions>
|
||||
#include <dust3d/base/debug.h>
|
||||
|
||||
static const QString &loadShaderSource(const QString &name)
|
||||
static const QString& loadShaderSource(const QString& name)
|
||||
{
|
||||
static std::map<QString, QString> s_shaderSources;
|
||||
auto findShader = s_shaderSources.find(name);
|
||||
|
@ -15,11 +15,11 @@ static const QString &loadShaderSource(const QString &name)
|
|||
QFile file(name);
|
||||
file.open(QFile::ReadOnly | QFile::Text);
|
||||
QTextStream stream(&file);
|
||||
auto insertResult = s_shaderSources.insert({name, stream.readAll()});
|
||||
auto insertResult = s_shaderSources.insert({ name, stream.readAll() });
|
||||
return insertResult.first->second;
|
||||
}
|
||||
|
||||
void ModelOpenGLProgram::addShaderFromResource(QOpenGLShader::ShaderType type, const char *resourceName)
|
||||
void ModelOpenGLProgram::addShaderFromResource(QOpenGLShader::ShaderType type, const char* resourceName)
|
||||
{
|
||||
if (!addShaderFromSourceCode(type, loadShaderSource(resourceName)))
|
||||
dust3dDebug << "Failed to addShaderFromResource, resource:" << resourceName << ", " << log().toStdString();
|
||||
|
@ -57,7 +57,7 @@ void ModelOpenGLProgram::updateMetalnessRoughnessAmbientOcclusionMapImage(std::u
|
|||
m_imageIsDirty = true;
|
||||
}
|
||||
|
||||
void ModelOpenGLProgram::activeAndBindTexture(int location, QOpenGLTexture *texture)
|
||||
void ModelOpenGLProgram::activeAndBindTexture(int location, QOpenGLTexture* texture)
|
||||
{
|
||||
if (0 == texture->textureId()) {
|
||||
dust3dDebug << "Expected texture with a bound id";
|
||||
|
@ -224,12 +224,12 @@ void ModelOpenGLProgram::releaseMaps()
|
|||
}
|
||||
}
|
||||
|
||||
int ModelOpenGLProgram::getUniformLocationByName(const std::string &name)
|
||||
int ModelOpenGLProgram::getUniformLocationByName(const std::string& name)
|
||||
{
|
||||
auto findLocation = m_uniformLocationMap.find(name);
|
||||
if (findLocation != m_uniformLocationMap.end())
|
||||
return findLocation->second;
|
||||
int location = uniformLocation(name.c_str());
|
||||
m_uniformLocationMap.insert({name, location});
|
||||
m_uniformLocationMap.insert({ name, location });
|
||||
return location;
|
||||
}
|
||||
|
|
|
@ -1,17 +1,16 @@
|
|||
#ifndef DUST3D_APPLICATION_MODEL_OPENGL_PROGRAM_H_
|
||||
#define DUST3D_APPLICATION_MODEL_OPENGL_PROGRAM_H_
|
||||
|
||||
#include <memory>
|
||||
#include <QOpenGLShaderProgram>
|
||||
#include <QOpenGLShader>
|
||||
#include <QOpenGLTexture>
|
||||
#include <QMutex>
|
||||
#include <QOpenGLShader>
|
||||
#include <QOpenGLShaderProgram>
|
||||
#include <QOpenGLTexture>
|
||||
#include <memory>
|
||||
|
||||
class ModelOpenGLProgram: public QOpenGLShaderProgram
|
||||
{
|
||||
class ModelOpenGLProgram : public QOpenGLShaderProgram {
|
||||
public:
|
||||
void load(bool isCoreProfile=false);
|
||||
int getUniformLocationByName(const std::string &name);
|
||||
void load(bool isCoreProfile = false);
|
||||
int getUniformLocationByName(const std::string& name);
|
||||
bool isCoreProfile() const;
|
||||
void bindMaps();
|
||||
void releaseMaps();
|
||||
|
@ -23,8 +22,8 @@ public:
|
|||
bool hasAmbientOcclusionMap = false);
|
||||
|
||||
private:
|
||||
void addShaderFromResource(QOpenGLShader::ShaderType type, const char *resourceName);
|
||||
void activeAndBindTexture(int location, QOpenGLTexture *texture);
|
||||
void addShaderFromResource(QOpenGLShader::ShaderType type, const char* resourceName);
|
||||
void activeAndBindTexture(int location, QOpenGLTexture* texture);
|
||||
|
||||
bool m_isLoaded = false;
|
||||
bool m_isCoreProfile = false;
|
||||
|
|
|
@ -1,11 +1,11 @@
|
|||
#include <QMouseEvent>
|
||||
#include <QCoreApplication>
|
||||
#include <QGuiApplication>
|
||||
#include <cmath>
|
||||
#include <QVector4D>
|
||||
#include <QSurfaceFormat>
|
||||
#include "model_widget.h"
|
||||
#include "dds_file.h"
|
||||
#include <QCoreApplication>
|
||||
#include <QGuiApplication>
|
||||
#include <QMouseEvent>
|
||||
#include <QSurfaceFormat>
|
||||
#include <QVector4D>
|
||||
#include <cmath>
|
||||
|
||||
float ModelWidget::m_minZoomRatio = 5.0;
|
||||
float ModelWidget::m_maxZoomRatio = 80.0;
|
||||
|
@ -18,8 +18,8 @@ QString ModelWidget::m_openGLVersion = "";
|
|||
QString ModelWidget::m_openGLShadingLanguageVersion = "";
|
||||
bool ModelWidget::m_openGLIsCoreProfile = false;
|
||||
|
||||
ModelWidget::ModelWidget(QWidget *parent) :
|
||||
QOpenGLWidget(parent)
|
||||
ModelWidget::ModelWidget(QWidget* parent)
|
||||
: QOpenGLWidget(parent)
|
||||
{
|
||||
setAttribute(Qt::WA_AlwaysStackOnTop);
|
||||
setAttribute(Qt::WA_TranslucentBackground);
|
||||
|
@ -32,22 +32,22 @@ ModelWidget::ModelWidget(QWidget *parent) :
|
|||
setContextMenuPolicy(Qt::CustomContextMenu);
|
||||
|
||||
m_widthInPixels = width() * window()->devicePixelRatio();
|
||||
m_heightInPixels = height() * window()->devicePixelRatio();
|
||||
m_heightInPixels = height() * window()->devicePixelRatio();
|
||||
|
||||
zoom(200);
|
||||
}
|
||||
|
||||
const QVector3D &ModelWidget::eyePosition()
|
||||
const QVector3D& ModelWidget::eyePosition()
|
||||
{
|
||||
return m_eyePosition;
|
||||
return m_eyePosition;
|
||||
}
|
||||
|
||||
const QVector3D &ModelWidget::moveToPosition()
|
||||
const QVector3D& ModelWidget::moveToPosition()
|
||||
{
|
||||
return m_moveToPosition;
|
||||
}
|
||||
|
||||
void ModelWidget::setEyePosition(const QVector3D &eyePosition)
|
||||
void ModelWidget::setEyePosition(const QVector3D& eyePosition)
|
||||
{
|
||||
m_eyePosition = eyePosition;
|
||||
emit eyePositionChanged(m_eyePosition);
|
||||
|
@ -130,7 +130,7 @@ void ModelWidget::disableCullFace()
|
|||
m_enableCullFace = false;
|
||||
}
|
||||
|
||||
void ModelWidget::setMoveToPosition(const QVector3D &moveToPosition)
|
||||
void ModelWidget::setMoveToPosition(const QVector3D& moveToPosition)
|
||||
{
|
||||
m_moveToPosition = moveToPosition;
|
||||
}
|
||||
|
@ -144,13 +144,13 @@ void ModelWidget::updateProjectionMatrix()
|
|||
|
||||
void ModelWidget::resizeGL(int w, int h)
|
||||
{
|
||||
m_widthInPixels = w * window()->devicePixelRatio();
|
||||
m_heightInPixels = h * window()->devicePixelRatio();
|
||||
m_widthInPixels = w * window()->devicePixelRatio();
|
||||
m_heightInPixels = h * window()->devicePixelRatio();
|
||||
updateProjectionMatrix();
|
||||
emit renderParametersChanged();
|
||||
}
|
||||
|
||||
std::pair<QVector3D, QVector3D> ModelWidget::screenPositionToMouseRay(const QPoint &screenPosition)
|
||||
std::pair<QVector3D, QVector3D> ModelWidget::screenPositionToMouseRay(const QPoint& screenPosition)
|
||||
{
|
||||
auto modelView = m_camera * m_world;
|
||||
float x = qMax(qMin(screenPosition.x(), width() - 1), 0);
|
||||
|
@ -190,12 +190,11 @@ void ModelWidget::toggleRotation()
|
|||
}
|
||||
}
|
||||
|
||||
bool ModelWidget::inputMousePressEventFromOtherWidget(QMouseEvent *event, bool notGraphics)
|
||||
bool ModelWidget::inputMousePressEventFromOtherWidget(QMouseEvent* event, bool notGraphics)
|
||||
{
|
||||
bool shouldStartMove = false;
|
||||
if (event->button() == Qt::LeftButton) {
|
||||
if ((notGraphics || QGuiApplication::queryKeyboardModifiers().testFlag(Qt::AltModifier)) &&
|
||||
!QGuiApplication::queryKeyboardModifiers().testFlag(Qt::ControlModifier)) {
|
||||
if ((notGraphics || QGuiApplication::queryKeyboardModifiers().testFlag(Qt::AltModifier)) && !QGuiApplication::queryKeyboardModifiers().testFlag(Qt::ControlModifier)) {
|
||||
shouldStartMove = m_moveEnabled;
|
||||
}
|
||||
if (!shouldStartMove && !m_mousePickTargetPositionInModelSpace.isNull())
|
||||
|
@ -216,7 +215,7 @@ bool ModelWidget::inputMousePressEventFromOtherWidget(QMouseEvent *event, bool n
|
|||
return false;
|
||||
}
|
||||
|
||||
bool ModelWidget::inputMouseReleaseEventFromOtherWidget(QMouseEvent *event)
|
||||
bool ModelWidget::inputMouseReleaseEventFromOtherWidget(QMouseEvent* event)
|
||||
{
|
||||
Q_UNUSED(event);
|
||||
if (m_moveStarted) {
|
||||
|
@ -235,7 +234,7 @@ void ModelWidget::canvasResized()
|
|||
resize(parentWidget()->size());
|
||||
}
|
||||
|
||||
bool ModelWidget::inputMouseMoveEventFromOtherWidget(QMouseEvent *event)
|
||||
bool ModelWidget::inputMouseMoveEventFromOtherWidget(QMouseEvent* event)
|
||||
{
|
||||
QPoint pos = convertInputPosFromOtherWidget(event);
|
||||
|
||||
|
@ -251,8 +250,7 @@ bool ModelWidget::inputMouseMoveEventFromOtherWidget(QMouseEvent *event)
|
|||
int dx = pos.x() - m_lastPos.x();
|
||||
int dy = pos.y() - m_lastPos.y();
|
||||
|
||||
if ((event->buttons() & Qt::MidButton) ||
|
||||
(m_moveStarted && (event->buttons() & Qt::LeftButton))) {
|
||||
if ((event->buttons() & Qt::MidButton) || (m_moveStarted && (event->buttons() & Qt::LeftButton))) {
|
||||
if (QGuiApplication::queryKeyboardModifiers().testFlag(Qt::ShiftModifier)) {
|
||||
if (m_moveStarted) {
|
||||
if (m_moveAndZoomByWindow) {
|
||||
|
@ -287,12 +285,12 @@ bool ModelWidget::inputMouseMoveEventFromOtherWidget(QMouseEvent *event)
|
|||
return true;
|
||||
}
|
||||
|
||||
QPoint ModelWidget::convertInputPosFromOtherWidget(QMouseEvent *event)
|
||||
QPoint ModelWidget::convertInputPosFromOtherWidget(QMouseEvent* event)
|
||||
{
|
||||
return mapFromGlobal(event->globalPos());
|
||||
}
|
||||
|
||||
bool ModelWidget::inputWheelEventFromOtherWidget(QWheelEvent *event)
|
||||
bool ModelWidget::inputWheelEventFromOtherWidget(QWheelEvent* event)
|
||||
{
|
||||
if (m_moveStarted)
|
||||
return true;
|
||||
|
@ -359,7 +357,7 @@ void ModelWidget::setMousePickRadius(float radius)
|
|||
update();
|
||||
}
|
||||
|
||||
void ModelWidget::updateMesh(ModelMesh *mesh)
|
||||
void ModelWidget::updateMesh(ModelMesh* mesh)
|
||||
{
|
||||
if (!m_modelOpenGLProgram)
|
||||
m_modelOpenGLProgram = std::make_unique<ModelOpenGLProgram>();
|
||||
|
@ -378,7 +376,7 @@ void ModelWidget::updateMesh(ModelMesh *mesh)
|
|||
update();
|
||||
}
|
||||
|
||||
void ModelWidget::updateWireframeMesh(MonochromeMesh *mesh)
|
||||
void ModelWidget::updateWireframeMesh(MonochromeMesh* mesh)
|
||||
{
|
||||
if (!m_wireframeOpenGLObject)
|
||||
m_wireframeOpenGLObject = std::make_unique<MonochromeOpenGLObject>();
|
||||
|
@ -389,12 +387,12 @@ void ModelWidget::updateWireframeMesh(MonochromeMesh *mesh)
|
|||
|
||||
int ModelWidget::widthInPixels()
|
||||
{
|
||||
return m_widthInPixels;
|
||||
return m_widthInPixels;
|
||||
}
|
||||
|
||||
int ModelWidget::heightInPixels()
|
||||
{
|
||||
return m_heightInPixels;
|
||||
return m_heightInPixels;
|
||||
}
|
||||
|
||||
void ModelWidget::enableMove(bool enabled)
|
||||
|
@ -417,22 +415,22 @@ void ModelWidget::setMoveAndZoomByWindow(bool byWindow)
|
|||
m_moveAndZoomByWindow = byWindow;
|
||||
}
|
||||
|
||||
void ModelWidget::mousePressEvent(QMouseEvent *event)
|
||||
void ModelWidget::mousePressEvent(QMouseEvent* event)
|
||||
{
|
||||
inputMousePressEventFromOtherWidget(event, m_notGraphics);
|
||||
}
|
||||
|
||||
void ModelWidget::mouseMoveEvent(QMouseEvent *event)
|
||||
void ModelWidget::mouseMoveEvent(QMouseEvent* event)
|
||||
{
|
||||
inputMouseMoveEventFromOtherWidget(event);
|
||||
}
|
||||
|
||||
void ModelWidget::wheelEvent(QWheelEvent *event)
|
||||
void ModelWidget::wheelEvent(QWheelEvent* event)
|
||||
{
|
||||
inputWheelEventFromOtherWidget(event);
|
||||
}
|
||||
|
||||
void ModelWidget::mouseReleaseEvent(QMouseEvent *event)
|
||||
void ModelWidget::mouseReleaseEvent(QMouseEvent* event)
|
||||
{
|
||||
inputMouseReleaseEventFromOtherWidget(event);
|
||||
}
|
||||
|
@ -442,7 +440,7 @@ void ModelWidget::setNotGraphics(bool notGraphics)
|
|||
m_notGraphics = notGraphics;
|
||||
}
|
||||
|
||||
void ModelWidget::normalizeAngle(int &angle)
|
||||
void ModelWidget::normalizeAngle(int& angle)
|
||||
{
|
||||
while (angle < 0)
|
||||
angle += 360 * 16;
|
||||
|
@ -455,10 +453,10 @@ void ModelWidget::initializeGL()
|
|||
connect(context(), &QOpenGLContext::aboutToBeDestroyed, this, &ModelWidget::cleanup);
|
||||
|
||||
if (m_openGLVersion.isEmpty()) {
|
||||
QOpenGLFunctions *f = QOpenGLContext::currentContext()->functions();
|
||||
const char *openGLVersion = (const char *)f->glGetString(GL_VERSION);
|
||||
QOpenGLFunctions* f = QOpenGLContext::currentContext()->functions();
|
||||
const char* openGLVersion = (const char*)f->glGetString(GL_VERSION);
|
||||
m_openGLVersion = nullptr != openGLVersion ? openGLVersion : "<Unknown>";
|
||||
const char *shadingLanguageVersion = (const char *)glGetString(GL_SHADING_LANGUAGE_VERSION);
|
||||
const char* shadingLanguageVersion = (const char*)glGetString(GL_SHADING_LANGUAGE_VERSION);
|
||||
m_openGLShadingLanguageVersion = nullptr != shadingLanguageVersion ? shadingLanguageVersion : "<Unknown>";
|
||||
m_openGLIsCoreProfile = QSurfaceFormat::defaultFormat().profile() == QSurfaceFormat::CoreProfile;
|
||||
}
|
||||
|
@ -466,7 +464,7 @@ void ModelWidget::initializeGL()
|
|||
|
||||
void ModelWidget::paintGL()
|
||||
{
|
||||
QOpenGLFunctions *f = QOpenGLContext::currentContext()->functions();
|
||||
QOpenGLFunctions* f = QOpenGLContext::currentContext()->functions();
|
||||
|
||||
f->glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
|
||||
f->glEnable(GL_BLEND);
|
||||
|
@ -485,7 +483,7 @@ void ModelWidget::paintGL()
|
|||
f->glEnable(GL_POLYGON_OFFSET_FILL);
|
||||
f->glPolygonOffset(1.0, 1.0);
|
||||
|
||||
f->glViewport(0, 0, m_widthInPixels, m_heightInPixels);
|
||||
f->glViewport(0, 0, m_widthInPixels, m_heightInPixels);
|
||||
|
||||
m_world.setToIdentity();
|
||||
m_world.rotate(m_xRot / 16.0f, 1, 0, 0);
|
||||
|
|
|
@ -1,27 +1,26 @@
|
|||
#ifndef DUST3D_APPLICATION_MODEL_WIDGET_H_
|
||||
#define DUST3D_APPLICATION_MODEL_WIDGET_H_
|
||||
|
||||
#include <memory>
|
||||
#include <QOpenGLWidget>
|
||||
#include <QOpenGLBuffer>
|
||||
#include <QOpenGLTexture>
|
||||
#include "model_mesh.h"
|
||||
#include "model_opengl_object.h"
|
||||
#include "model_opengl_program.h"
|
||||
#include "monochrome_mesh.h"
|
||||
#include "monochrome_opengl_object.h"
|
||||
#include "monochrome_opengl_program.h"
|
||||
#include <QMatrix4x4>
|
||||
#include <QMutex>
|
||||
#include <QVector2D>
|
||||
#include <QTimer>
|
||||
#include <QOpenGLBuffer>
|
||||
#include <QOpenGLTexture>
|
||||
#include <QOpenGLWidget>
|
||||
#include <QString>
|
||||
#include "model_mesh.h"
|
||||
#include "model_opengl_program.h"
|
||||
#include "model_opengl_object.h"
|
||||
#include "monochrome_mesh.h"
|
||||
#include "monochrome_opengl_program.h"
|
||||
#include "monochrome_opengl_object.h"
|
||||
#include <QTimer>
|
||||
#include <QVector2D>
|
||||
#include <memory>
|
||||
|
||||
class ModelWidget : public QOpenGLWidget
|
||||
{
|
||||
class ModelWidget : public QOpenGLWidget {
|
||||
Q_OBJECT
|
||||
signals:
|
||||
void mouseRayChanged(const QVector3D &near, const QVector3D &far);
|
||||
void mouseRayChanged(const QVector3D& near, const QVector3D& far);
|
||||
void mousePressed();
|
||||
void mouseReleased();
|
||||
void addMouseRadius(float radius);
|
||||
|
@ -29,13 +28,14 @@ signals:
|
|||
void xRotationChanged(int angle);
|
||||
void yRotationChanged(int angle);
|
||||
void zRotationChanged(int angle);
|
||||
void eyePositionChanged(const QVector3D &eyePosition);
|
||||
void moveToPositionChanged(const QVector3D &moveToPosition);
|
||||
void eyePositionChanged(const QVector3D& eyePosition);
|
||||
void moveToPositionChanged(const QVector3D& moveToPosition);
|
||||
|
||||
public:
|
||||
ModelWidget(QWidget *parent = 0);
|
||||
ModelWidget(QWidget* parent = 0);
|
||||
~ModelWidget();
|
||||
void updateMesh(ModelMesh *mesh);
|
||||
void updateWireframeMesh(MonochromeMesh *mesh);
|
||||
void updateMesh(ModelMesh* mesh);
|
||||
void updateWireframeMesh(MonochromeMesh* mesh);
|
||||
void toggleWireframe();
|
||||
bool isWireframeVisible();
|
||||
void toggleRotation();
|
||||
|
@ -44,40 +44,42 @@ public:
|
|||
void enableMousePicking(bool enabled);
|
||||
void setMoveAndZoomByWindow(bool byWindow);
|
||||
void disableCullFace();
|
||||
void setMoveToPosition(const QVector3D &moveToPosition);
|
||||
bool inputMousePressEventFromOtherWidget(QMouseEvent *event, bool notGraphics=false);
|
||||
bool inputMouseMoveEventFromOtherWidget(QMouseEvent *event);
|
||||
bool inputWheelEventFromOtherWidget(QWheelEvent *event);
|
||||
bool inputMouseReleaseEventFromOtherWidget(QMouseEvent *event);
|
||||
QPoint convertInputPosFromOtherWidget(QMouseEvent *event);
|
||||
void setMoveToPosition(const QVector3D& moveToPosition);
|
||||
bool inputMousePressEventFromOtherWidget(QMouseEvent* event, bool notGraphics = false);
|
||||
bool inputMouseMoveEventFromOtherWidget(QMouseEvent* event);
|
||||
bool inputWheelEventFromOtherWidget(QWheelEvent* event);
|
||||
bool inputMouseReleaseEventFromOtherWidget(QMouseEvent* event);
|
||||
QPoint convertInputPosFromOtherWidget(QMouseEvent* event);
|
||||
int widthInPixels();
|
||||
int heightInPixels();
|
||||
void setNotGraphics(bool notGraphics);
|
||||
int xRot();
|
||||
int yRot();
|
||||
int zRot();
|
||||
const QVector3D &eyePosition();
|
||||
const QVector3D &moveToPosition();
|
||||
const QString &openGLVersion();
|
||||
const QVector3D& eyePosition();
|
||||
const QVector3D& moveToPosition();
|
||||
const QString& openGLVersion();
|
||||
public slots:
|
||||
void setXRotation(int angle);
|
||||
void setYRotation(int angle);
|
||||
void setZRotation(int angle);
|
||||
void setEyePosition(const QVector3D &eyePosition);
|
||||
void setEyePosition(const QVector3D& eyePosition);
|
||||
void cleanup();
|
||||
void zoom(float delta);
|
||||
void setMousePickTargetPositionInModelSpace(QVector3D position);
|
||||
void setMousePickRadius(float radius);
|
||||
void reRender();
|
||||
void canvasResized();
|
||||
|
||||
protected:
|
||||
void initializeGL() override;
|
||||
void paintGL() override;
|
||||
void resizeGL(int width, int height) override;
|
||||
void mousePressEvent(QMouseEvent *event) override;
|
||||
void mouseMoveEvent(QMouseEvent *event) override;
|
||||
void wheelEvent(QWheelEvent *event) override;
|
||||
void mouseReleaseEvent(QMouseEvent *event) override;
|
||||
void mousePressEvent(QMouseEvent* event) override;
|
||||
void mouseMoveEvent(QMouseEvent* event) override;
|
||||
void wheelEvent(QWheelEvent* event) override;
|
||||
void mouseReleaseEvent(QMouseEvent* event) override;
|
||||
|
||||
private:
|
||||
int m_xRot = m_defaultXRotation;
|
||||
int m_yRot = m_defaultYRotation;
|
||||
|
@ -103,7 +105,7 @@ private:
|
|||
QPoint m_moveStartPos;
|
||||
QRect m_moveStartGeometry;
|
||||
int m_modelInitialHeight = 0;
|
||||
QTimer *m_rotationTimer = nullptr;
|
||||
QTimer* m_rotationTimer = nullptr;
|
||||
int m_widthInPixels = 0;
|
||||
int m_heightInPixels = 0;
|
||||
QVector3D m_moveToPosition;
|
||||
|
@ -111,11 +113,12 @@ private:
|
|||
bool m_enableCullFace = true;
|
||||
bool m_notGraphics = false;
|
||||
bool m_isWireframeVisible = false;
|
||||
std::pair<QVector3D, QVector3D> screenPositionToMouseRay(const QPoint &screenPosition);
|
||||
std::pair<QVector3D, QVector3D> screenPositionToMouseRay(const QPoint& screenPosition);
|
||||
void updateProjectionMatrix();
|
||||
void normalizeAngle(int &angle);
|
||||
void normalizeAngle(int& angle);
|
||||
void drawModel();
|
||||
void drawWireframe();
|
||||
|
||||
public:
|
||||
static int m_defaultXRotation;
|
||||
static int m_defaultYRotation;
|
||||
|
|
|
@ -1,59 +1,57 @@
|
|||
#include <set>
|
||||
#include "monochrome_mesh.h"
|
||||
#include <set>
|
||||
|
||||
MonochromeMesh::MonochromeMesh(const MonochromeMesh &mesh)
|
||||
MonochromeMesh::MonochromeMesh(const MonochromeMesh& mesh)
|
||||
{
|
||||
m_lineVertices = mesh.m_lineVertices;
|
||||
}
|
||||
|
||||
MonochromeMesh::MonochromeMesh(MonochromeMesh &&mesh)
|
||||
MonochromeMesh::MonochromeMesh(MonochromeMesh&& mesh)
|
||||
{
|
||||
m_lineVertices = std::move(mesh.m_lineVertices);
|
||||
}
|
||||
|
||||
MonochromeMesh::MonochromeMesh(const dust3d::Object &object)
|
||||
MonochromeMesh::MonochromeMesh(const dust3d::Object& object)
|
||||
{
|
||||
std::set<std::pair<size_t, size_t>> halfEdges;
|
||||
for (const auto &face: object.triangleAndQuads) {
|
||||
for (const auto& face : object.triangleAndQuads) {
|
||||
if (3 == face.size()) {
|
||||
halfEdges.insert({face[0], face[1]});
|
||||
halfEdges.insert({face[1], face[0]});
|
||||
halfEdges.insert({face[1], face[2]});
|
||||
halfEdges.insert({face[2], face[1]});
|
||||
halfEdges.insert({face[2], face[0]});
|
||||
halfEdges.insert({face[0], face[2]});
|
||||
halfEdges.insert({ face[0], face[1] });
|
||||
halfEdges.insert({ face[1], face[0] });
|
||||
halfEdges.insert({ face[1], face[2] });
|
||||
halfEdges.insert({ face[2], face[1] });
|
||||
halfEdges.insert({ face[2], face[0] });
|
||||
halfEdges.insert({ face[0], face[2] });
|
||||
continue;
|
||||
}
|
||||
halfEdges.insert({face[0], face[1]});
|
||||
halfEdges.insert({face[1], face[0]});
|
||||
halfEdges.insert({face[1], face[2]});
|
||||
halfEdges.insert({face[2], face[1]});
|
||||
halfEdges.insert({face[2], face[3]});
|
||||
halfEdges.insert({face[3], face[2]});
|
||||
halfEdges.insert({face[3], face[0]});
|
||||
halfEdges.insert({face[0], face[3]});
|
||||
halfEdges.insert({ face[0], face[1] });
|
||||
halfEdges.insert({ face[1], face[0] });
|
||||
halfEdges.insert({ face[1], face[2] });
|
||||
halfEdges.insert({ face[2], face[1] });
|
||||
halfEdges.insert({ face[2], face[3] });
|
||||
halfEdges.insert({ face[3], face[2] });
|
||||
halfEdges.insert({ face[3], face[0] });
|
||||
halfEdges.insert({ face[0], face[3] });
|
||||
}
|
||||
m_lineVertices.reserve(halfEdges.size() * 2);
|
||||
for (const auto &halfEdge: halfEdges) {
|
||||
for (const auto& halfEdge : halfEdges) {
|
||||
// For two halfedges shared one edge, only output one line
|
||||
if (halfEdge.first > halfEdge.second)
|
||||
continue;
|
||||
const auto &from = object.vertices[halfEdge.first];
|
||||
const auto &to = object.vertices[halfEdge.second];
|
||||
const auto& from = object.vertices[halfEdge.first];
|
||||
const auto& to = object.vertices[halfEdge.second];
|
||||
m_lineVertices.emplace_back(MonochromeOpenGLVertex {
|
||||
(GLfloat)from.x(),
|
||||
(GLfloat)from.y(),
|
||||
(GLfloat)from.z()
|
||||
});
|
||||
(GLfloat)from.z() });
|
||||
m_lineVertices.emplace_back(MonochromeOpenGLVertex {
|
||||
(GLfloat)to.x(),
|
||||
(GLfloat)to.y(),
|
||||
(GLfloat)to.z()
|
||||
});
|
||||
(GLfloat)to.z() });
|
||||
}
|
||||
}
|
||||
|
||||
const MonochromeOpenGLVertex *MonochromeMesh::lineVertices()
|
||||
const MonochromeOpenGLVertex* MonochromeMesh::lineVertices()
|
||||
{
|
||||
if (m_lineVertices.empty())
|
||||
return nullptr;
|
||||
|
|
|
@ -1,21 +1,20 @@
|
|||
#ifndef DUST3D_APPLICATION_MONOCHROME_MESH_H_
|
||||
#define DUST3D_APPLICATION_MONOCHROME_MESH_H_
|
||||
|
||||
#include <memory>
|
||||
#include <dust3d/base/object.h>
|
||||
#include "monochrome_opengl_vertex.h"
|
||||
#include <dust3d/base/object.h>
|
||||
#include <memory>
|
||||
|
||||
class MonochromeMesh
|
||||
{
|
||||
class MonochromeMesh {
|
||||
public:
|
||||
MonochromeMesh(const MonochromeMesh &mesh);
|
||||
MonochromeMesh(MonochromeMesh &&mesh);
|
||||
MonochromeMesh(const dust3d::Object &object);
|
||||
const MonochromeOpenGLVertex *lineVertices();
|
||||
MonochromeMesh(const MonochromeMesh& mesh);
|
||||
MonochromeMesh(MonochromeMesh&& mesh);
|
||||
MonochromeMesh(const dust3d::Object& object);
|
||||
const MonochromeOpenGLVertex* lineVertices();
|
||||
int lineVertexCount();
|
||||
|
||||
private:
|
||||
std::vector<MonochromeOpenGLVertex> m_lineVertices;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
#include <dust3d/base/debug.h>
|
||||
#include <QOpenGLFunctions>
|
||||
#include <QOpenGLContext>
|
||||
#include "monochrome_opengl_object.h"
|
||||
#include <QOpenGLContext>
|
||||
#include <QOpenGLFunctions>
|
||||
#include <dust3d/base/debug.h>
|
||||
|
||||
void MonochromeOpenGLObject::update(std::unique_ptr<MonochromeMesh> mesh)
|
||||
{
|
||||
|
@ -15,7 +15,7 @@ void MonochromeOpenGLObject::draw()
|
|||
copyMeshToOpenGL();
|
||||
if (0 == m_meshLineVertexCount)
|
||||
return;
|
||||
QOpenGLFunctions *f = QOpenGLContext::currentContext()->functions();
|
||||
QOpenGLFunctions* f = QOpenGLContext::currentContext()->functions();
|
||||
QOpenGLVertexArrayObject::Binder binder(&m_vertexArrayObject);
|
||||
f->glDrawArrays(GL_LINES, 0, m_meshLineVertexCount);
|
||||
}
|
||||
|
@ -43,13 +43,13 @@ void MonochromeOpenGLObject::copyMeshToOpenGL()
|
|||
m_buffer.bind();
|
||||
m_buffer.allocate(mesh->lineVertices(), mesh->lineVertexCount() * sizeof(MonochromeOpenGLVertex));
|
||||
m_meshLineVertexCount = mesh->lineVertexCount();
|
||||
QOpenGLFunctions *f = QOpenGLContext::currentContext()->functions();
|
||||
QOpenGLFunctions* f = QOpenGLContext::currentContext()->functions();
|
||||
f->glEnableVertexAttribArray(0);
|
||||
f->glEnableVertexAttribArray(1);
|
||||
f->glEnableVertexAttribArray(2);
|
||||
f->glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, sizeof(MonochromeOpenGLVertex), 0);
|
||||
f->glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, sizeof(MonochromeOpenGLVertex), reinterpret_cast<void *>(3 * sizeof(GLfloat)));
|
||||
f->glVertexAttribPointer(2, 1, GL_FLOAT, GL_FALSE, sizeof(MonochromeOpenGLVertex), reinterpret_cast<void *>(6 * sizeof(GLfloat)));
|
||||
f->glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, sizeof(MonochromeOpenGLVertex), reinterpret_cast<void*>(3 * sizeof(GLfloat)));
|
||||
f->glVertexAttribPointer(2, 1, GL_FLOAT, GL_FALSE, sizeof(MonochromeOpenGLVertex), reinterpret_cast<void*>(6 * sizeof(GLfloat)));
|
||||
m_buffer.release();
|
||||
}
|
||||
}
|
|
@ -1,17 +1,17 @@
|
|||
#ifndef DUST3D_APPLICATION_MONOCHROME_OPENGL_OBJECT_H_
|
||||
#define DUST3D_APPLICATION_MONOCHROME_OPENGL_OBJECT_H_
|
||||
|
||||
#include <memory>
|
||||
#include <QMutex>
|
||||
#include <QOpenGLVertexArrayObject>
|
||||
#include <QOpenGLBuffer>
|
||||
#include "monochrome_mesh.h"
|
||||
#include <QMutex>
|
||||
#include <QOpenGLBuffer>
|
||||
#include <QOpenGLVertexArrayObject>
|
||||
#include <memory>
|
||||
|
||||
class MonochromeOpenGLObject
|
||||
{
|
||||
class MonochromeOpenGLObject {
|
||||
public:
|
||||
void update(std::unique_ptr<MonochromeMesh> mesh);
|
||||
void draw();
|
||||
|
||||
private:
|
||||
void copyMeshToOpenGL();
|
||||
QOpenGLVertexArrayObject m_vertexArrayObject;
|
||||
|
|
|
@ -1,9 +1,9 @@
|
|||
#include <QOpenGLFunctions>
|
||||
#include <QFile>
|
||||
#include <dust3d/base/debug.h>
|
||||
#include "monochrome_opengl_program.h"
|
||||
#include <QFile>
|
||||
#include <QOpenGLFunctions>
|
||||
#include <dust3d/base/debug.h>
|
||||
|
||||
static const QString &loadShaderSource(const QString &name)
|
||||
static const QString& loadShaderSource(const QString& name)
|
||||
{
|
||||
static std::map<QString, QString> s_shaderSources;
|
||||
auto findShader = s_shaderSources.find(name);
|
||||
|
@ -13,11 +13,11 @@ static const QString &loadShaderSource(const QString &name)
|
|||
QFile file(name);
|
||||
file.open(QFile::ReadOnly | QFile::Text);
|
||||
QTextStream stream(&file);
|
||||
auto insertResult = s_shaderSources.insert({name, stream.readAll()});
|
||||
auto insertResult = s_shaderSources.insert({ name, stream.readAll() });
|
||||
return insertResult.first->second;
|
||||
}
|
||||
|
||||
void MonochromeOpenGLProgram::addShaderFromResource(QOpenGLShader::ShaderType type, const char *resourceName)
|
||||
void MonochromeOpenGLProgram::addShaderFromResource(QOpenGLShader::ShaderType type, const char* resourceName)
|
||||
{
|
||||
if (!addShaderFromSourceCode(type, loadShaderSource(resourceName)))
|
||||
dust3dDebug << "Failed to addShaderFromResource, resource:" << resourceName << ", " << log().toStdString();
|
||||
|
@ -49,12 +49,12 @@ void MonochromeOpenGLProgram::load(bool isCoreProfile)
|
|||
m_isLoaded = true;
|
||||
}
|
||||
|
||||
int MonochromeOpenGLProgram::getUniformLocationByName(const std::string &name)
|
||||
int MonochromeOpenGLProgram::getUniformLocationByName(const std::string& name)
|
||||
{
|
||||
auto findLocation = m_uniformLocationMap.find(name);
|
||||
if (findLocation != m_uniformLocationMap.end())
|
||||
return findLocation->second;
|
||||
int location = uniformLocation(name.c_str());
|
||||
m_uniformLocationMap.insert({name, location});
|
||||
m_uniformLocationMap.insert({ name, location });
|
||||
return location;
|
||||
}
|
||||
|
|
|
@ -1,19 +1,18 @@
|
|||
#ifndef DUST3D_APPLICATION_MONOCHROME_OPENGL_PROGRAM_H_
|
||||
#define DUST3D_APPLICATION_MONOCHROME_OPENGL_PROGRAM_H_
|
||||
|
||||
#include <memory>
|
||||
#include <QOpenGLShaderProgram>
|
||||
#include <QOpenGLShader>
|
||||
#include <QOpenGLShaderProgram>
|
||||
#include <memory>
|
||||
|
||||
class MonochromeOpenGLProgram: public QOpenGLShaderProgram
|
||||
{
|
||||
class MonochromeOpenGLProgram : public QOpenGLShaderProgram {
|
||||
public:
|
||||
void load(bool isCoreProfile=false);
|
||||
int getUniformLocationByName(const std::string &name);
|
||||
void load(bool isCoreProfile = false);
|
||||
int getUniformLocationByName(const std::string& name);
|
||||
bool isCoreProfile() const;
|
||||
|
||||
private:
|
||||
void addShaderFromResource(QOpenGLShader::ShaderType type, const char *resourceName);
|
||||
void addShaderFromResource(QOpenGLShader::ShaderType type, const char* resourceName);
|
||||
|
||||
bool m_isLoaded = false;
|
||||
bool m_isCoreProfile = false;
|
||||
|
|
|
@ -1,27 +1,27 @@
|
|||
#include <QVBoxLayout>
|
||||
#include <QWidgetAction>
|
||||
#include <QMenu>
|
||||
#include "part_manage_widget.h"
|
||||
#include "component_list_model.h"
|
||||
#include "component_preview_grid_widget.h"
|
||||
#include "component_property_widget.h"
|
||||
#include "component_list_model.h"
|
||||
#include "theme.h"
|
||||
#include "document.h"
|
||||
#include "theme.h"
|
||||
#include <QMenu>
|
||||
#include <QVBoxLayout>
|
||||
#include <QWidgetAction>
|
||||
|
||||
PartManageWidget::PartManageWidget(Document *document, QWidget *parent):
|
||||
QWidget(parent),
|
||||
m_document(document)
|
||||
PartManageWidget::PartManageWidget(Document* document, QWidget* parent)
|
||||
: QWidget(parent)
|
||||
, m_document(document)
|
||||
{
|
||||
setContextMenuPolicy(Qt::CustomContextMenu);
|
||||
|
||||
QHBoxLayout *toolsLayout = new QHBoxLayout;
|
||||
QHBoxLayout* toolsLayout = new QHBoxLayout;
|
||||
toolsLayout->setSpacing(0);
|
||||
toolsLayout->setMargin(0);
|
||||
|
||||
setStyleSheet("QPushButton:disabled {border: 0; color: " + Theme::gray.name() + "}");
|
||||
|
||||
auto createButton = [](QChar icon, const QString &title) {
|
||||
QPushButton *button = new QPushButton(icon);
|
||||
auto createButton = [](QChar icon, const QString& title) {
|
||||
QPushButton* button = new QPushButton(icon);
|
||||
Theme::initIconButton(button);
|
||||
button->setToolTip(title);
|
||||
return button;
|
||||
|
@ -58,50 +58,50 @@ PartManageWidget::PartManageWidget(Document *document, QWidget *parent):
|
|||
//connect(m_componentPreviewGridWidget->selectionModel(), &QItemSelectionModel::selectionChanged, this, &PartManageWidget::showSelectedComponentProperties);
|
||||
|
||||
connect(m_levelUpButton, &QPushButton::clicked, [this]() {
|
||||
const auto &parent = m_document->findComponentParent(this->m_componentPreviewGridWidget->componentListModel()->listingComponentId());
|
||||
const auto& parent = m_document->findComponentParent(this->m_componentPreviewGridWidget->componentListModel()->listingComponentId());
|
||||
if (nullptr == parent)
|
||||
return;
|
||||
this->m_componentPreviewGridWidget->componentListModel()->setListingComponentId(parent->id);
|
||||
});
|
||||
|
||||
connect(m_hideButton, &QPushButton::clicked, [this]() {
|
||||
for (const auto &partId: this->m_componentPreviewGridWidget->getSelectedPartIds())
|
||||
for (const auto& partId : this->m_componentPreviewGridWidget->getSelectedPartIds())
|
||||
this->m_document->setPartVisibleState(partId, false);
|
||||
this->m_document->saveSnapshot();
|
||||
});
|
||||
connect(m_showButton, &QPushButton::clicked, [this]() {
|
||||
for (const auto &partId: this->m_componentPreviewGridWidget->getSelectedPartIds())
|
||||
for (const auto& partId : this->m_componentPreviewGridWidget->getSelectedPartIds())
|
||||
this->m_document->setPartVisibleState(partId, true);
|
||||
this->m_document->saveSnapshot();
|
||||
});
|
||||
|
||||
connect(m_unlockButton, &QPushButton::clicked, [this]() {
|
||||
for (const auto &partId: this->m_componentPreviewGridWidget->getSelectedPartIds())
|
||||
for (const auto& partId : this->m_componentPreviewGridWidget->getSelectedPartIds())
|
||||
this->m_document->setPartLockState(partId, false);
|
||||
this->m_document->saveSnapshot();
|
||||
});
|
||||
connect(m_lockButton, &QPushButton::clicked, [this]() {
|
||||
for (const auto &partId: this->m_componentPreviewGridWidget->getSelectedPartIds())
|
||||
for (const auto& partId : this->m_componentPreviewGridWidget->getSelectedPartIds())
|
||||
this->m_document->setPartLockState(partId, true);
|
||||
this->m_document->saveSnapshot();
|
||||
});
|
||||
|
||||
connect(m_unlinkButton, &QPushButton::clicked, [this]() {
|
||||
for (const auto &partId: this->m_componentPreviewGridWidget->getSelectedPartIds())
|
||||
for (const auto& partId : this->m_componentPreviewGridWidget->getSelectedPartIds())
|
||||
this->m_document->setPartDisableState(partId, true);
|
||||
this->m_document->saveSnapshot();
|
||||
});
|
||||
connect(m_linkButton, &QPushButton::clicked, [this]() {
|
||||
for (const auto &partId: this->m_componentPreviewGridWidget->getSelectedPartIds())
|
||||
for (const auto& partId : this->m_componentPreviewGridWidget->getSelectedPartIds())
|
||||
this->m_document->setPartDisableState(partId, false);
|
||||
this->m_document->saveSnapshot();
|
||||
});
|
||||
|
||||
connect(m_selectButton, &QPushButton::clicked, [this]() {
|
||||
for (const auto &componentId: this->m_componentPreviewGridWidget->getSelectedComponentIds()) {
|
||||
for (const auto& componentId : this->m_componentPreviewGridWidget->getSelectedComponentIds()) {
|
||||
std::vector<dust3d::Uuid> partIds;
|
||||
this->m_document->collectComponentDescendantParts(componentId, partIds);
|
||||
for (const auto &partId: partIds)
|
||||
for (const auto& partId : partIds)
|
||||
emit this->selectPartOnCanvas(partId);
|
||||
}
|
||||
});
|
||||
|
@ -119,7 +119,7 @@ PartManageWidget::PartManageWidget(Document *document, QWidget *parent):
|
|||
|
||||
connect(this, &PartManageWidget::customContextMenuRequested, this, &PartManageWidget::showContextMenu);
|
||||
|
||||
QVBoxLayout *mainLayout = new QVBoxLayout;
|
||||
QVBoxLayout* mainLayout = new QVBoxLayout;
|
||||
mainLayout->addLayout(toolsLayout);
|
||||
mainLayout->addWidget(m_componentPreviewGridWidget);
|
||||
|
||||
|
@ -135,10 +135,10 @@ void PartManageWidget::showSelectedComponentProperties()
|
|||
if (componentIds.empty())
|
||||
return;
|
||||
|
||||
auto *propertyWidget = new ComponentPropertyWidget(m_document, componentIds);
|
||||
auto* propertyWidget = new ComponentPropertyWidget(m_document, componentIds);
|
||||
|
||||
auto menu = std::make_unique<QMenu>(this->parentWidget());
|
||||
QWidgetAction *widgetAction = new QWidgetAction(menu.get());
|
||||
QWidgetAction* widgetAction = new QWidgetAction(menu.get());
|
||||
widgetAction->setDefaultWidget(propertyWidget);
|
||||
menu->addAction(widgetAction);
|
||||
|
||||
|
@ -147,13 +147,12 @@ void PartManageWidget::showSelectedComponentProperties()
|
|||
x = QCursor::pos().x();
|
||||
menu->exec(QPoint(
|
||||
x - propertyWidget->width(),
|
||||
QCursor::pos().y()
|
||||
));
|
||||
QCursor::pos().y()));
|
||||
}
|
||||
|
||||
void PartManageWidget::selectComponentByPartId(const dust3d::Uuid &partId)
|
||||
void PartManageWidget::selectComponentByPartId(const dust3d::Uuid& partId)
|
||||
{
|
||||
const auto &part = m_document->findPart(partId);
|
||||
const auto& part = m_document->findPart(partId);
|
||||
if (nullptr == part)
|
||||
return;
|
||||
auto componentId = part->componentId;
|
||||
|
@ -163,7 +162,7 @@ void PartManageWidget::selectComponentByPartId(const dust3d::Uuid &partId)
|
|||
m_componentPreviewGridWidget->scrollTo(index);
|
||||
return;
|
||||
}
|
||||
const auto &component = m_document->findComponent(componentId);
|
||||
const auto& component = m_document->findComponent(componentId);
|
||||
if (nullptr == component)
|
||||
return;
|
||||
m_componentPreviewGridWidget->componentListModel()->setListingComponentId(component->parentId);
|
||||
|
@ -178,7 +177,7 @@ void PartManageWidget::selectComponentByPartId(const dust3d::Uuid &partId)
|
|||
|
||||
void PartManageWidget::updateLevelUpButton()
|
||||
{
|
||||
const auto &parent = m_document->findComponentParent(m_componentPreviewGridWidget->componentListModel()->listingComponentId());
|
||||
const auto& parent = m_document->findComponentParent(m_componentPreviewGridWidget->componentListModel()->listingComponentId());
|
||||
m_levelUpButton->setEnabled(nullptr != parent);
|
||||
}
|
||||
|
||||
|
@ -193,13 +192,13 @@ void PartManageWidget::updateToolButtons()
|
|||
bool enableUnlinkButton = false;
|
||||
bool enableLinkButton = false;
|
||||
bool enablePropertyButton = false;
|
||||
for (const auto &component: selectedComponents) {
|
||||
for (const auto& component : selectedComponents) {
|
||||
enablePropertyButton = true;
|
||||
enableSelectButton = true;
|
||||
if (component->linkToPartId.isNull()) {
|
||||
continue;
|
||||
}
|
||||
const auto &part = m_document->findPart(component->linkToPartId);
|
||||
const auto& part = m_document->findPart(component->linkToPartId);
|
||||
if (part->visible) {
|
||||
enableHideButton = true;
|
||||
} else {
|
||||
|
@ -229,14 +228,14 @@ void PartManageWidget::updateToolButtons()
|
|||
bool PartManageWidget::hasSelectedGroupedComponent()
|
||||
{
|
||||
auto selectedComponents = m_componentPreviewGridWidget->getSelectedComponents();
|
||||
for (auto &component: selectedComponents) {
|
||||
for (auto& component : selectedComponents) {
|
||||
if (!component->childrenIds.empty())
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
void PartManageWidget::showContextMenu(const QPoint &pos)
|
||||
void PartManageWidget::showContextMenu(const QPoint& pos)
|
||||
{
|
||||
auto selectedComponentIds = m_componentPreviewGridWidget->getSelectedComponentIds();
|
||||
if (selectedComponentIds.empty())
|
||||
|
@ -255,7 +254,7 @@ void PartManageWidget::showContextMenu(const QPoint &pos)
|
|||
QAction ungroupAction(tr("Ungroup"), this);
|
||||
if (hasSelectedGroupedComponent()) {
|
||||
connect(&ungroupAction, &QAction::triggered, this, [=]() {
|
||||
for (const auto &it: selectedComponentIds)
|
||||
for (const auto& it : selectedComponentIds)
|
||||
emit this->ungroupComponent(it);
|
||||
emit this->groupOperationAdded();
|
||||
});
|
||||
|
|
|
@ -1,41 +1,42 @@
|
|||
#ifndef DUST3D_APPLICATION_PART_MANAGE_WIDGET_H_
|
||||
#define DUST3D_APPLICATION_PART_MANAGE_WIDGET_H_
|
||||
|
||||
#include <dust3d/base/uuid.h>
|
||||
#include <QWidget>
|
||||
#include <dust3d/base/uuid.h>
|
||||
|
||||
class Document;
|
||||
class ComponentPreviewGridWidget;
|
||||
class ComponentPropertyWidget;
|
||||
class QPushButton;
|
||||
|
||||
class PartManageWidget: public QWidget
|
||||
{
|
||||
class PartManageWidget : public QWidget {
|
||||
Q_OBJECT
|
||||
signals:
|
||||
void unselectAllOnCanvas();
|
||||
void selectPartOnCanvas(const dust3d::Uuid &partId);
|
||||
void groupComponents(const std::vector<dust3d::Uuid> &componentIds);
|
||||
void ungroupComponent(const dust3d::Uuid &componentId);
|
||||
void selectPartOnCanvas(const dust3d::Uuid& partId);
|
||||
void groupComponents(const std::vector<dust3d::Uuid>& componentIds);
|
||||
void ungroupComponent(const dust3d::Uuid& componentId);
|
||||
void groupOperationAdded();
|
||||
public slots:
|
||||
void selectComponentByPartId(const dust3d::Uuid &partId);
|
||||
void selectComponentByPartId(const dust3d::Uuid& partId);
|
||||
void showSelectedComponentProperties();
|
||||
void showContextMenu(const QPoint &pos);
|
||||
void showContextMenu(const QPoint& pos);
|
||||
|
||||
public:
|
||||
PartManageWidget(Document *document, QWidget *parent=nullptr);
|
||||
PartManageWidget(Document* document, QWidget* parent = nullptr);
|
||||
|
||||
private:
|
||||
Document *m_document = nullptr;
|
||||
ComponentPreviewGridWidget *m_componentPreviewGridWidget = nullptr;
|
||||
QPushButton *m_levelUpButton = nullptr;
|
||||
QPushButton *m_selectButton = nullptr;
|
||||
QPushButton *m_lockButton = nullptr;
|
||||
QPushButton *m_unlockButton = nullptr;
|
||||
QPushButton *m_showButton = nullptr;
|
||||
QPushButton *m_hideButton = nullptr;
|
||||
QPushButton *m_unlinkButton = nullptr;
|
||||
QPushButton *m_linkButton = nullptr;
|
||||
QPushButton *m_propertyButton = nullptr;
|
||||
Document* m_document = nullptr;
|
||||
ComponentPreviewGridWidget* m_componentPreviewGridWidget = nullptr;
|
||||
QPushButton* m_levelUpButton = nullptr;
|
||||
QPushButton* m_selectButton = nullptr;
|
||||
QPushButton* m_lockButton = nullptr;
|
||||
QPushButton* m_unlockButton = nullptr;
|
||||
QPushButton* m_showButton = nullptr;
|
||||
QPushButton* m_hideButton = nullptr;
|
||||
QPushButton* m_unlinkButton = nullptr;
|
||||
QPushButton* m_linkButton = nullptr;
|
||||
QPushButton* m_propertyButton = nullptr;
|
||||
void updateToolButtons();
|
||||
void updateLevelUpButton();
|
||||
bool hasSelectedGroupedComponent();
|
||||
|
|
|
@ -1,10 +1,10 @@
|
|||
#include "preferences.h"
|
||||
|
||||
#define MAX_RECENT_FILES 7
|
||||
#define MAX_RECENT_FILES 7
|
||||
|
||||
Preferences &Preferences::instance()
|
||||
Preferences& Preferences::instance()
|
||||
{
|
||||
static Preferences *s_preferences = nullptr;
|
||||
static Preferences* s_preferences = nullptr;
|
||||
if (nullptr == s_preferences) {
|
||||
s_preferences = new Preferences;
|
||||
}
|
||||
|
@ -40,7 +40,7 @@ int Preferences::maxRecentFiles() const
|
|||
return MAX_RECENT_FILES;
|
||||
}
|
||||
|
||||
void Preferences::setCurrentFile(const QString &fileName)
|
||||
void Preferences::setCurrentFile(const QString& fileName)
|
||||
{
|
||||
QStringList files = m_settings.value("recentFileList").toStringList();
|
||||
|
||||
|
|
|
@ -5,19 +5,19 @@
|
|||
#include <QSize>
|
||||
#include <QStringList>
|
||||
|
||||
class Preferences : public QObject
|
||||
{
|
||||
class Preferences : public QObject {
|
||||
Q_OBJECT
|
||||
public:
|
||||
static Preferences &instance();
|
||||
static Preferences& instance();
|
||||
Preferences();
|
||||
QSize documentWindowSize() const;
|
||||
void setDocumentWindowSize(const QSize&);
|
||||
QStringList recentFileList() const;
|
||||
int maxRecentFiles() const;
|
||||
public slots:
|
||||
void setCurrentFile(const QString &fileName);
|
||||
void setCurrentFile(const QString& fileName);
|
||||
void reset();
|
||||
|
||||
private:
|
||||
QSettings m_settings;
|
||||
void loadDefault();
|
||||
|
|
|
@ -1,8 +1,8 @@
|
|||
#include "preview_grid_view.h"
|
||||
#include "theme.h"
|
||||
|
||||
PreviewGridView::PreviewGridView(QWidget *parent):
|
||||
QListView(parent)
|
||||
PreviewGridView::PreviewGridView(QWidget* parent)
|
||||
: QListView(parent)
|
||||
{
|
||||
QPalette viewPalette = palette();
|
||||
viewPalette.setColor(QPalette::Window, Qt::transparent);
|
||||
|
@ -13,9 +13,7 @@ PreviewGridView::PreviewGridView(QWidget *parent):
|
|||
auto margin = Theme::previewIconMargin;
|
||||
auto borderRadius = Theme::previewIconBorderRadius;
|
||||
setStyleSheet(
|
||||
"QListView::item {border:" + QString::number(borderSize) + "px solid transparent; margin:" + QString::number(margin) + "px; background-color: " + Theme::gray.name() +"; border-radius: " + QString::number(borderRadius) + ";}" +
|
||||
"QListView::item:selected {border-color: " + Theme::red.name() + ";}"
|
||||
);
|
||||
"QListView::item {border:" + QString::number(borderSize) + "px solid transparent; margin:" + QString::number(margin) + "px; background-color: " + Theme::gray.name() + "; border-radius: " + QString::number(borderRadius) + ";}" + "QListView::item:selected {border-color: " + Theme::red.name() + ";}");
|
||||
|
||||
setViewMode(QListView::IconMode);
|
||||
setGridSize(QSize(Theme::partPreviewImageSize, Theme::partPreviewImageSize));
|
||||
|
|
|
@ -3,11 +3,10 @@
|
|||
|
||||
#include <QListView>
|
||||
|
||||
class PreviewGridView: public QListView
|
||||
{
|
||||
class PreviewGridView : public QListView {
|
||||
Q_OBJECT
|
||||
public:
|
||||
PreviewGridView(QWidget *parent=nullptr);
|
||||
PreviewGridView(QWidget* parent = nullptr);
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
#include <QDebug>
|
||||
#include "skeleton_document.h"
|
||||
#include <QDebug>
|
||||
|
||||
const SkeletonNode *SkeletonDocument::findNode(dust3d::Uuid nodeId) const
|
||||
const SkeletonNode* SkeletonDocument::findNode(dust3d::Uuid nodeId) const
|
||||
{
|
||||
auto it = nodeMap.find(nodeId);
|
||||
if (it == nodeMap.end())
|
||||
|
@ -9,7 +9,7 @@ const SkeletonNode *SkeletonDocument::findNode(dust3d::Uuid nodeId) const
|
|||
return &it->second;
|
||||
}
|
||||
|
||||
const SkeletonEdge *SkeletonDocument::findEdge(dust3d::Uuid edgeId) const
|
||||
const SkeletonEdge* SkeletonDocument::findEdge(dust3d::Uuid edgeId) const
|
||||
{
|
||||
auto it = edgeMap.find(edgeId);
|
||||
if (it == edgeMap.end())
|
||||
|
@ -17,7 +17,7 @@ const SkeletonEdge *SkeletonDocument::findEdge(dust3d::Uuid edgeId) const
|
|||
return &it->second;
|
||||
}
|
||||
|
||||
const SkeletonPart *SkeletonDocument::findPart(dust3d::Uuid partId) const
|
||||
const SkeletonPart* SkeletonDocument::findPart(dust3d::Uuid partId) const
|
||||
{
|
||||
auto it = partMap.find(partId);
|
||||
if (it == partMap.end())
|
||||
|
@ -25,9 +25,9 @@ const SkeletonPart *SkeletonDocument::findPart(dust3d::Uuid partId) const
|
|||
return &it->second;
|
||||
}
|
||||
|
||||
const SkeletonEdge *SkeletonDocument::findEdgeByNodes(dust3d::Uuid firstNodeId, dust3d::Uuid secondNodeId) const
|
||||
const SkeletonEdge* SkeletonDocument::findEdgeByNodes(dust3d::Uuid firstNodeId, dust3d::Uuid secondNodeId) const
|
||||
{
|
||||
const SkeletonNode *firstNode = nullptr;
|
||||
const SkeletonNode* firstNode = nullptr;
|
||||
firstNode = findNode(firstNodeId);
|
||||
if (nullptr == firstNode) {
|
||||
return nullptr;
|
||||
|
@ -43,18 +43,18 @@ const SkeletonEdge *SkeletonDocument::findEdgeByNodes(dust3d::Uuid firstNodeId,
|
|||
return nullptr;
|
||||
}
|
||||
|
||||
void SkeletonDocument::findAllNeighbors(dust3d::Uuid nodeId, std::set<dust3d::Uuid> &neighbors) const
|
||||
void SkeletonDocument::findAllNeighbors(dust3d::Uuid nodeId, std::set<dust3d::Uuid>& neighbors) const
|
||||
{
|
||||
const auto &node = findNode(nodeId);
|
||||
const auto& node = findNode(nodeId);
|
||||
if (nullptr == node) {
|
||||
return;
|
||||
}
|
||||
for (const auto &edgeId: node->edgeIds) {
|
||||
const auto &edge = findEdge(edgeId);
|
||||
for (const auto& edgeId : node->edgeIds) {
|
||||
const auto& edge = findEdge(edgeId);
|
||||
if (nullptr == edge) {
|
||||
continue;
|
||||
}
|
||||
const auto &neighborNodeId = edge->neighborOf(nodeId);
|
||||
const auto& neighborNodeId = edge->neighborOf(nodeId);
|
||||
if (neighborNodeId.isNull()) {
|
||||
continue;
|
||||
}
|
||||
|
@ -68,7 +68,7 @@ void SkeletonDocument::findAllNeighbors(dust3d::Uuid nodeId, std::set<dust3d::Uu
|
|||
|
||||
bool SkeletonDocument::isNodeConnectable(dust3d::Uuid nodeId) const
|
||||
{
|
||||
const auto &node = findNode(nodeId);
|
||||
const auto& node = findNode(nodeId);
|
||||
if (nullptr == node)
|
||||
return false;
|
||||
if (node->edgeIds.size() < 2)
|
||||
|
@ -78,7 +78,7 @@ bool SkeletonDocument::isNodeConnectable(dust3d::Uuid nodeId) const
|
|||
|
||||
void SkeletonDocument::reduceNode(dust3d::Uuid nodeId)
|
||||
{
|
||||
const SkeletonNode *node = findNode(nodeId);
|
||||
const SkeletonNode* node = findNode(nodeId);
|
||||
if (nullptr == node) {
|
||||
return;
|
||||
}
|
||||
|
@ -87,11 +87,11 @@ void SkeletonDocument::reduceNode(dust3d::Uuid nodeId)
|
|||
}
|
||||
dust3d::Uuid firstEdgeId = node->edgeIds[0];
|
||||
dust3d::Uuid secondEdgeId = node->edgeIds[1];
|
||||
const SkeletonEdge *firstEdge = findEdge(firstEdgeId);
|
||||
const SkeletonEdge* firstEdge = findEdge(firstEdgeId);
|
||||
if (nullptr == firstEdge) {
|
||||
return;
|
||||
}
|
||||
const SkeletonEdge *secondEdge = findEdge(secondEdgeId);
|
||||
const SkeletonEdge* secondEdge = findEdge(secondEdgeId);
|
||||
if (nullptr == secondEdge) {
|
||||
return;
|
||||
}
|
||||
|
@ -103,7 +103,7 @@ void SkeletonDocument::reduceNode(dust3d::Uuid nodeId)
|
|||
|
||||
void SkeletonDocument::breakEdge(dust3d::Uuid edgeId)
|
||||
{
|
||||
const SkeletonEdge *edge = findEdge(edgeId);
|
||||
const SkeletonEdge* edge = findEdge(edgeId);
|
||||
if (nullptr == edge) {
|
||||
return;
|
||||
}
|
||||
|
@ -112,11 +112,11 @@ void SkeletonDocument::breakEdge(dust3d::Uuid edgeId)
|
|||
}
|
||||
dust3d::Uuid firstNodeId = edge->nodeIds[0];
|
||||
dust3d::Uuid secondNodeId = edge->nodeIds[1];
|
||||
const SkeletonNode *firstNode = findNode(firstNodeId);
|
||||
const SkeletonNode* firstNode = findNode(firstNodeId);
|
||||
if (nullptr == firstNode) {
|
||||
return;
|
||||
}
|
||||
const SkeletonNode *secondNode = findNode(secondNodeId);
|
||||
const SkeletonNode* secondNode = findNode(secondNodeId);
|
||||
if (nullptr == secondNode) {
|
||||
return;
|
||||
}
|
||||
|
@ -134,7 +134,7 @@ void SkeletonDocument::breakEdge(dust3d::Uuid edgeId)
|
|||
|
||||
void SkeletonDocument::reverseEdge(dust3d::Uuid edgeId)
|
||||
{
|
||||
SkeletonEdge *edge = (SkeletonEdge *)findEdge(edgeId);
|
||||
SkeletonEdge* edge = (SkeletonEdge*)findEdge(edgeId);
|
||||
if (nullptr == edge) {
|
||||
return;
|
||||
}
|
||||
|
@ -151,13 +151,13 @@ void SkeletonDocument::reverseEdge(dust3d::Uuid edgeId)
|
|||
|
||||
void SkeletonDocument::removeEdge(dust3d::Uuid edgeId)
|
||||
{
|
||||
const SkeletonEdge *edge = findEdge(edgeId);
|
||||
const SkeletonEdge* edge = findEdge(edgeId);
|
||||
if (nullptr == edge) {
|
||||
return;
|
||||
}
|
||||
if (isPartReadonly(edge->partId))
|
||||
return;
|
||||
const SkeletonPart *oldPart = findPart(edge->partId);
|
||||
const SkeletonPart* oldPart = findPart(edge->partId);
|
||||
if (nullptr == oldPart) {
|
||||
return;
|
||||
}
|
||||
|
@ -169,7 +169,7 @@ void SkeletonDocument::removeEdge(dust3d::Uuid edgeId)
|
|||
std::vector<dust3d::Uuid> newPartIds;
|
||||
for (auto groupIt = groups.begin(); groupIt != groups.end(); groupIt++) {
|
||||
const auto newUuid = dust3d::Uuid::createUuid();
|
||||
SkeletonPart &part = partMap[newUuid];
|
||||
SkeletonPart& part = partMap[newUuid];
|
||||
part.id = newUuid;
|
||||
part.copyAttributes(*oldPart);
|
||||
part.name = nextPartName;
|
||||
|
@ -189,7 +189,7 @@ void SkeletonDocument::removeEdge(dust3d::Uuid edgeId)
|
|||
}
|
||||
}
|
||||
addPartToComponent(part.id, findComponentParentId(part.componentId));
|
||||
newPartNodeNumMap.push_back({part.id, part.nodeIds.size()});
|
||||
newPartNodeNumMap.push_back({ part.id, part.nodeIds.size() });
|
||||
newPartIds.push_back(part.id);
|
||||
emit partAdded(part.id);
|
||||
}
|
||||
|
@ -206,8 +206,7 @@ void SkeletonDocument::removeEdge(dust3d::Uuid edgeId)
|
|||
removePart(oldPartId);
|
||||
|
||||
if (!newPartNodeNumMap.empty()) {
|
||||
std::sort(newPartNodeNumMap.begin(), newPartNodeNumMap.end(), [&](
|
||||
const std::pair<dust3d::Uuid, size_t> &first, const std::pair<dust3d::Uuid, size_t> &second) {
|
||||
std::sort(newPartNodeNumMap.begin(), newPartNodeNumMap.end(), [&](const std::pair<dust3d::Uuid, size_t>& first, const std::pair<dust3d::Uuid, size_t>& second) {
|
||||
return first.second > second.second;
|
||||
});
|
||||
updateLinkedPart(oldPartId, newPartNodeNumMap[0].first);
|
||||
|
@ -218,13 +217,13 @@ void SkeletonDocument::removeEdge(dust3d::Uuid edgeId)
|
|||
|
||||
void SkeletonDocument::removeNode(dust3d::Uuid nodeId)
|
||||
{
|
||||
const SkeletonNode *node = findNode(nodeId);
|
||||
const SkeletonNode* node = findNode(nodeId);
|
||||
if (nullptr == node) {
|
||||
return;
|
||||
}
|
||||
if (isPartReadonly(node->partId))
|
||||
return;
|
||||
const SkeletonPart *oldPart = findPart(node->partId);
|
||||
const SkeletonPart* oldPart = findPart(node->partId);
|
||||
if (nullptr == oldPart) {
|
||||
return;
|
||||
}
|
||||
|
@ -236,7 +235,7 @@ void SkeletonDocument::removeNode(dust3d::Uuid nodeId)
|
|||
std::vector<dust3d::Uuid> newPartIds;
|
||||
for (auto groupIt = groups.begin(); groupIt != groups.end(); groupIt++) {
|
||||
const auto newUuid = dust3d::Uuid::createUuid();
|
||||
SkeletonPart &part = partMap[newUuid];
|
||||
SkeletonPart& part = partMap[newUuid];
|
||||
part.id = newUuid;
|
||||
part.copyAttributes(*oldPart);
|
||||
part.name = nextPartName;
|
||||
|
@ -256,7 +255,7 @@ void SkeletonDocument::removeNode(dust3d::Uuid nodeId)
|
|||
}
|
||||
}
|
||||
addPartToComponent(part.id, findComponentParentId(part.componentId));
|
||||
newPartNodeNumMap.push_back({part.id, part.nodeIds.size()});
|
||||
newPartNodeNumMap.push_back({ part.id, part.nodeIds.size() });
|
||||
newPartIds.push_back(part.id);
|
||||
emit partAdded(part.id);
|
||||
}
|
||||
|
@ -279,8 +278,7 @@ void SkeletonDocument::removeNode(dust3d::Uuid nodeId)
|
|||
removePart(oldPartId);
|
||||
|
||||
if (!newPartNodeNumMap.empty()) {
|
||||
std::sort(newPartNodeNumMap.begin(), newPartNodeNumMap.end(), [&](
|
||||
const std::pair<dust3d::Uuid, size_t> &first, const std::pair<dust3d::Uuid, size_t> &second) {
|
||||
std::sort(newPartNodeNumMap.begin(), newPartNodeNumMap.end(), [&](const std::pair<dust3d::Uuid, size_t>& first, const std::pair<dust3d::Uuid, size_t>& second) {
|
||||
return first.second > second.second;
|
||||
});
|
||||
updateLinkedPart(oldPartId, newPartNodeNumMap[0].first);
|
||||
|
@ -302,11 +300,11 @@ void SkeletonDocument::addNodeWithId(dust3d::Uuid nodeId, float x, float y, floa
|
|||
dust3d::Uuid SkeletonDocument::createNode(dust3d::Uuid nodeId, float x, float y, float z, float radius, dust3d::Uuid fromNodeId)
|
||||
{
|
||||
dust3d::Uuid partId;
|
||||
const SkeletonNode *fromNode = nullptr;
|
||||
const SkeletonNode* fromNode = nullptr;
|
||||
bool newPartAdded = false;
|
||||
if (fromNodeId.isNull()) {
|
||||
const auto newUuid = dust3d::Uuid::createUuid();
|
||||
SkeletonPart &part = partMap[newUuid];
|
||||
SkeletonPart& part = partMap[newUuid];
|
||||
part.id = newUuid;
|
||||
partId = part.id;
|
||||
emit partAdded(partId);
|
||||
|
@ -355,11 +353,11 @@ dust3d::Uuid SkeletonDocument::createNode(dust3d::Uuid nodeId, float x, float y,
|
|||
return node.id;
|
||||
}
|
||||
|
||||
void SkeletonDocument::joinNodeAndNeiborsToGroup(std::vector<dust3d::Uuid> *group, dust3d::Uuid nodeId, std::set<dust3d::Uuid> *visitMap, dust3d::Uuid noUseEdgeId)
|
||||
void SkeletonDocument::joinNodeAndNeiborsToGroup(std::vector<dust3d::Uuid>* group, dust3d::Uuid nodeId, std::set<dust3d::Uuid>* visitMap, dust3d::Uuid noUseEdgeId)
|
||||
{
|
||||
if (nodeId.isNull() || visitMap->find(nodeId) != visitMap->end())
|
||||
return;
|
||||
const SkeletonNode *node = findNode(nodeId);
|
||||
const SkeletonNode* node = findNode(nodeId);
|
||||
if (nullptr == node) {
|
||||
return;
|
||||
}
|
||||
|
@ -368,7 +366,7 @@ void SkeletonDocument::joinNodeAndNeiborsToGroup(std::vector<dust3d::Uuid> *grou
|
|||
for (auto edgeIt = node->edgeIds.begin(); edgeIt != node->edgeIds.end(); edgeIt++) {
|
||||
if (noUseEdgeId == *edgeIt)
|
||||
continue;
|
||||
const SkeletonEdge *edge = findEdge(*edgeIt);
|
||||
const SkeletonEdge* edge = findEdge(*edgeIt);
|
||||
if (nullptr == edge) {
|
||||
continue;
|
||||
}
|
||||
|
@ -378,14 +376,14 @@ void SkeletonDocument::joinNodeAndNeiborsToGroup(std::vector<dust3d::Uuid> *grou
|
|||
}
|
||||
}
|
||||
|
||||
void SkeletonDocument::splitPartByNode(std::vector<std::vector<dust3d::Uuid>> *groups, dust3d::Uuid nodeId)
|
||||
void SkeletonDocument::splitPartByNode(std::vector<std::vector<dust3d::Uuid>>* groups, dust3d::Uuid nodeId)
|
||||
{
|
||||
const SkeletonNode *node = findNode(nodeId);
|
||||
const SkeletonNode* node = findNode(nodeId);
|
||||
std::set<dust3d::Uuid> visitMap;
|
||||
visitMap.insert(nodeId);
|
||||
for (auto edgeIt = node->edgeIds.begin(); edgeIt != node->edgeIds.end(); edgeIt++) {
|
||||
std::vector<dust3d::Uuid> group;
|
||||
const SkeletonEdge *edge = findEdge(*edgeIt);
|
||||
const SkeletonEdge* edge = findEdge(*edgeIt);
|
||||
if (nullptr == edge) {
|
||||
continue;
|
||||
}
|
||||
|
@ -395,9 +393,9 @@ void SkeletonDocument::splitPartByNode(std::vector<std::vector<dust3d::Uuid>> *g
|
|||
}
|
||||
}
|
||||
|
||||
void SkeletonDocument::splitPartByEdge(std::vector<std::vector<dust3d::Uuid>> *groups, dust3d::Uuid edgeId)
|
||||
void SkeletonDocument::splitPartByEdge(std::vector<std::vector<dust3d::Uuid>>* groups, dust3d::Uuid edgeId)
|
||||
{
|
||||
const SkeletonEdge *edge = findEdge(edgeId);
|
||||
const SkeletonEdge* edge = findEdge(edgeId);
|
||||
if (nullptr == edge) {
|
||||
return;
|
||||
}
|
||||
|
@ -410,7 +408,7 @@ void SkeletonDocument::splitPartByEdge(std::vector<std::vector<dust3d::Uuid>> *g
|
|||
}
|
||||
}
|
||||
|
||||
const SkeletonComponent *SkeletonDocument::findComponentParent(dust3d::Uuid componentId) const
|
||||
const SkeletonComponent* SkeletonDocument::findComponentParent(dust3d::Uuid componentId) const
|
||||
{
|
||||
auto component = componentMap.find(componentId);
|
||||
if (component == componentMap.end()) {
|
||||
|
@ -420,7 +418,7 @@ const SkeletonComponent *SkeletonDocument::findComponentParent(dust3d::Uuid comp
|
|||
if (component->second.parentId.isNull())
|
||||
return &rootComponent;
|
||||
|
||||
return (SkeletonComponent *)findComponent(component->second.parentId);
|
||||
return (SkeletonComponent*)findComponent(component->second.parentId);
|
||||
}
|
||||
|
||||
dust3d::Uuid SkeletonDocument::findComponentParentId(dust3d::Uuid componentId) const
|
||||
|
@ -435,7 +433,7 @@ dust3d::Uuid SkeletonDocument::findComponentParentId(dust3d::Uuid componentId) c
|
|||
|
||||
void SkeletonDocument::moveComponentUp(dust3d::Uuid componentId)
|
||||
{
|
||||
SkeletonComponent *parent = (SkeletonComponent *)findComponentParent(componentId);
|
||||
SkeletonComponent* parent = (SkeletonComponent*)findComponentParent(componentId);
|
||||
if (nullptr == parent)
|
||||
return;
|
||||
|
||||
|
@ -449,7 +447,7 @@ void SkeletonDocument::moveComponentUp(dust3d::Uuid componentId)
|
|||
|
||||
void SkeletonDocument::moveComponentDown(dust3d::Uuid componentId)
|
||||
{
|
||||
SkeletonComponent *parent = (SkeletonComponent *)findComponentParent(componentId);
|
||||
SkeletonComponent* parent = (SkeletonComponent*)findComponentParent(componentId);
|
||||
if (nullptr == parent)
|
||||
return;
|
||||
|
||||
|
@ -463,7 +461,7 @@ void SkeletonDocument::moveComponentDown(dust3d::Uuid componentId)
|
|||
|
||||
void SkeletonDocument::moveComponentToTop(dust3d::Uuid componentId)
|
||||
{
|
||||
SkeletonComponent *parent = (SkeletonComponent *)findComponentParent(componentId);
|
||||
SkeletonComponent* parent = (SkeletonComponent*)findComponentParent(componentId);
|
||||
if (nullptr == parent)
|
||||
return;
|
||||
|
||||
|
@ -477,7 +475,7 @@ void SkeletonDocument::moveComponentToTop(dust3d::Uuid componentId)
|
|||
|
||||
void SkeletonDocument::moveComponentToBottom(dust3d::Uuid componentId)
|
||||
{
|
||||
SkeletonComponent *parent = (SkeletonComponent *)findComponentParent(componentId);
|
||||
SkeletonComponent* parent = (SkeletonComponent*)findComponentParent(componentId);
|
||||
if (nullptr == parent)
|
||||
return;
|
||||
|
||||
|
@ -520,11 +518,11 @@ void SkeletonDocument::setComponentExpandState(dust3d::Uuid componentId, bool ex
|
|||
emit optionsChanged();
|
||||
}
|
||||
|
||||
void SkeletonDocument::ungroupComponent(const dust3d::Uuid &componentId)
|
||||
void SkeletonDocument::ungroupComponent(const dust3d::Uuid& componentId)
|
||||
{
|
||||
if (componentId.isNull())
|
||||
return;
|
||||
SkeletonComponent *component = (SkeletonComponent *)findComponent(componentId);
|
||||
SkeletonComponent* component = (SkeletonComponent*)findComponent(componentId);
|
||||
if (nullptr == component) {
|
||||
dust3dDebug << "Component not found:" << componentId.toString();
|
||||
return;
|
||||
|
@ -532,15 +530,15 @@ void SkeletonDocument::ungroupComponent(const dust3d::Uuid &componentId)
|
|||
if (component->childrenIds.empty())
|
||||
return;
|
||||
auto childrenIds = component->childrenIds;
|
||||
SkeletonComponent *newParent = (SkeletonComponent *)findComponentParent(componentId);
|
||||
SkeletonComponent* newParent = (SkeletonComponent*)findComponentParent(componentId);
|
||||
if (nullptr == newParent) {
|
||||
dust3dDebug << "Expected parent component to be found, component:" << componentId.toString();
|
||||
return;
|
||||
}
|
||||
auto newParentId = newParent->id;
|
||||
newParent->replaceChildWithOthers(componentId, childrenIds);
|
||||
for (const auto &childId: childrenIds) {
|
||||
SkeletonComponent *child = (SkeletonComponent *)findComponent(childId);
|
||||
for (const auto& childId : childrenIds) {
|
||||
SkeletonComponent* child = (SkeletonComponent*)findComponent(childId);
|
||||
if (nullptr == child)
|
||||
continue;
|
||||
child->parentId = newParentId;
|
||||
|
@ -551,7 +549,7 @@ void SkeletonDocument::ungroupComponent(const dust3d::Uuid &componentId)
|
|||
emit skeletonChanged();
|
||||
}
|
||||
|
||||
void SkeletonDocument::groupComponents(const std::vector<dust3d::Uuid> &componentIds)
|
||||
void SkeletonDocument::groupComponents(const std::vector<dust3d::Uuid>& componentIds)
|
||||
{
|
||||
if (componentIds.empty())
|
||||
return;
|
||||
|
@ -563,7 +561,7 @@ void SkeletonDocument::groupComponents(const std::vector<dust3d::Uuid> &componen
|
|||
|
||||
auto it = componentIds.begin();
|
||||
|
||||
SkeletonComponent *oldParent = (SkeletonComponent *)findComponentParent(*it);
|
||||
SkeletonComponent* oldParent = (SkeletonComponent*)findComponentParent(*it);
|
||||
if (nullptr == oldParent) {
|
||||
dust3dDebug << "Expected parent component to be found, component:" << it->toString();
|
||||
return;
|
||||
|
@ -574,7 +572,7 @@ void SkeletonDocument::groupComponents(const std::vector<dust3d::Uuid> &componen
|
|||
oldParent->removeChild(*it);
|
||||
}
|
||||
|
||||
for (const auto &componentId: componentIds) {
|
||||
for (const auto& componentId : componentIds) {
|
||||
auto component = componentMap.find(componentId);
|
||||
if (component == componentMap.end()) {
|
||||
continue;
|
||||
|
@ -594,10 +592,10 @@ void SkeletonDocument::groupComponents(const std::vector<dust3d::Uuid> &componen
|
|||
|
||||
void SkeletonDocument::createNewChildComponent(dust3d::Uuid parentComponentId)
|
||||
{
|
||||
SkeletonComponent *parentComponent = (SkeletonComponent *)findComponent(parentComponentId);
|
||||
SkeletonComponent* parentComponent = (SkeletonComponent*)findComponent(parentComponentId);
|
||||
if (!parentComponent->linkToPartId.isNull()) {
|
||||
parentComponentId = parentComponent->parentId;
|
||||
parentComponent = (SkeletonComponent *)findComponent(parentComponentId);
|
||||
parentComponent = (SkeletonComponent*)findComponent(parentComponentId);
|
||||
}
|
||||
|
||||
SkeletonComponent newComponent(dust3d::Uuid::createUuid());
|
||||
|
@ -659,10 +657,10 @@ void SkeletonDocument::removePartDontCareComponent(dust3d::Uuid partId)
|
|||
|
||||
partMap.erase(part);
|
||||
|
||||
for (const auto &nodeId: removedNodeIds) {
|
||||
for (const auto& nodeId : removedNodeIds) {
|
||||
emit nodeRemoved(nodeId);
|
||||
}
|
||||
for (const auto &edgeId: removedEdgeIds) {
|
||||
for (const auto& edgeId : removedEdgeIds) {
|
||||
emit edgeRemoved(edgeId);
|
||||
}
|
||||
emit partRemoved(partId);
|
||||
|
@ -712,7 +710,7 @@ void SkeletonDocument::removeComponentRecursively(dust3d::Uuid componentId)
|
|||
}
|
||||
|
||||
auto childrenIds = component->second.childrenIds;
|
||||
for (const auto &childId: childrenIds) {
|
||||
for (const auto& childId : childrenIds) {
|
||||
removeComponentRecursively(childId);
|
||||
}
|
||||
|
||||
|
@ -735,7 +733,7 @@ void SkeletonDocument::removeComponentRecursively(dust3d::Uuid componentId)
|
|||
void SkeletonDocument::setCurrentCanvasComponentId(dust3d::Uuid componentId)
|
||||
{
|
||||
m_currentCanvasComponentId = componentId;
|
||||
const SkeletonComponent *component = findComponent(m_currentCanvasComponentId);
|
||||
const SkeletonComponent* component = findComponent(m_currentCanvasComponentId);
|
||||
if (nullptr == component) {
|
||||
m_currentCanvasComponentId = dust3d::Uuid();
|
||||
} else {
|
||||
|
@ -770,7 +768,7 @@ void SkeletonDocument::addComponent(dust3d::Uuid parentId)
|
|||
|
||||
bool SkeletonDocument::isDescendantComponent(dust3d::Uuid componentId, dust3d::Uuid suspiciousId)
|
||||
{
|
||||
const SkeletonComponent *loopComponent = findComponentParent(suspiciousId);
|
||||
const SkeletonComponent* loopComponent = findComponentParent(suspiciousId);
|
||||
while (nullptr != loopComponent) {
|
||||
if (loopComponent->id == componentId)
|
||||
return true;
|
||||
|
@ -864,9 +862,9 @@ void SkeletonDocument::setPartDisableState(dust3d::Uuid partId, bool disabled)
|
|||
emit skeletonChanged();
|
||||
}
|
||||
|
||||
void SkeletonDocument::collectComponentDescendantParts(dust3d::Uuid componentId, std::vector<dust3d::Uuid> &partIds) const
|
||||
void SkeletonDocument::collectComponentDescendantParts(dust3d::Uuid componentId, std::vector<dust3d::Uuid>& partIds) const
|
||||
{
|
||||
const SkeletonComponent *component = findComponent(componentId);
|
||||
const SkeletonComponent* component = findComponent(componentId);
|
||||
if (nullptr == component)
|
||||
return;
|
||||
|
||||
|
@ -875,14 +873,14 @@ void SkeletonDocument::collectComponentDescendantParts(dust3d::Uuid componentId,
|
|||
return;
|
||||
}
|
||||
|
||||
for (const auto &childId: component->childrenIds) {
|
||||
for (const auto& childId : component->childrenIds) {
|
||||
collectComponentDescendantParts(childId, partIds);
|
||||
}
|
||||
}
|
||||
|
||||
void SkeletonDocument::collectComponentDescendantComponents(dust3d::Uuid componentId, std::vector<dust3d::Uuid> &componentIds) const
|
||||
void SkeletonDocument::collectComponentDescendantComponents(dust3d::Uuid componentId, std::vector<dust3d::Uuid>& componentIds) const
|
||||
{
|
||||
const SkeletonComponent *component = findComponent(componentId);
|
||||
const SkeletonComponent* component = findComponent(componentId);
|
||||
if (nullptr == component)
|
||||
return;
|
||||
|
||||
|
@ -890,7 +888,7 @@ void SkeletonDocument::collectComponentDescendantComponents(dust3d::Uuid compone
|
|||
return;
|
||||
}
|
||||
|
||||
for (const auto &childId: component->childrenIds) {
|
||||
for (const auto& childId : component->childrenIds) {
|
||||
componentIds.push_back(childId);
|
||||
collectComponentDescendantComponents(childId, componentIds);
|
||||
}
|
||||
|
@ -901,10 +899,10 @@ void SkeletonDocument::hideOtherComponents(dust3d::Uuid componentId)
|
|||
std::vector<dust3d::Uuid> partIds;
|
||||
collectComponentDescendantParts(componentId, partIds);
|
||||
std::set<dust3d::Uuid> partIdSet;
|
||||
for (const auto &partId: partIds) {
|
||||
for (const auto& partId : partIds) {
|
||||
partIdSet.insert(partId);
|
||||
}
|
||||
for (const auto &part: partMap) {
|
||||
for (const auto& part : partMap) {
|
||||
if (partIdSet.find(part.first) != partIdSet.end())
|
||||
continue;
|
||||
setPartVisibleState(part.first, false);
|
||||
|
@ -916,10 +914,10 @@ void SkeletonDocument::lockOtherComponents(dust3d::Uuid componentId)
|
|||
std::vector<dust3d::Uuid> partIds;
|
||||
collectComponentDescendantParts(componentId, partIds);
|
||||
std::set<dust3d::Uuid> partIdSet;
|
||||
for (const auto &partId: partIds) {
|
||||
for (const auto& partId : partIds) {
|
||||
partIdSet.insert(partId);
|
||||
}
|
||||
for (const auto &part: partMap) {
|
||||
for (const auto& part : partMap) {
|
||||
if (partIdSet.find(part.first) != partIdSet.end())
|
||||
continue;
|
||||
setPartLockState(part.first, true);
|
||||
|
@ -928,14 +926,14 @@ void SkeletonDocument::lockOtherComponents(dust3d::Uuid componentId)
|
|||
|
||||
void SkeletonDocument::hideAllComponents()
|
||||
{
|
||||
for (const auto &part: partMap) {
|
||||
for (const auto& part : partMap) {
|
||||
setPartVisibleState(part.first, false);
|
||||
}
|
||||
}
|
||||
|
||||
void SkeletonDocument::showAllComponents()
|
||||
{
|
||||
for (const auto &part: partMap) {
|
||||
for (const auto& part : partMap) {
|
||||
setPartVisibleState(part.first, true);
|
||||
}
|
||||
}
|
||||
|
@ -943,7 +941,7 @@ void SkeletonDocument::showAllComponents()
|
|||
void SkeletonDocument::showOrHideAllComponents()
|
||||
{
|
||||
bool foundVisiblePart = false;
|
||||
for (const auto &part: partMap) {
|
||||
for (const auto& part : partMap) {
|
||||
if (part.second.visible) {
|
||||
foundVisiblePart = true;
|
||||
}
|
||||
|
@ -956,7 +954,7 @@ void SkeletonDocument::showOrHideAllComponents()
|
|||
|
||||
void SkeletonDocument::collapseAllComponents()
|
||||
{
|
||||
for (const auto &component: componentMap) {
|
||||
for (const auto& component : componentMap) {
|
||||
if (!component.second.linkToPartId.isNull())
|
||||
continue;
|
||||
setComponentExpandState(component.first, false);
|
||||
|
@ -965,7 +963,7 @@ void SkeletonDocument::collapseAllComponents()
|
|||
|
||||
void SkeletonDocument::expandAllComponents()
|
||||
{
|
||||
for (const auto &component: componentMap) {
|
||||
for (const auto& component : componentMap) {
|
||||
if (!component.second.linkToPartId.isNull())
|
||||
continue;
|
||||
setComponentExpandState(component.first, true);
|
||||
|
@ -974,14 +972,14 @@ void SkeletonDocument::expandAllComponents()
|
|||
|
||||
void SkeletonDocument::lockAllComponents()
|
||||
{
|
||||
for (const auto &part: partMap) {
|
||||
for (const auto& part : partMap) {
|
||||
setPartLockState(part.first, true);
|
||||
}
|
||||
}
|
||||
|
||||
void SkeletonDocument::unlockAllComponents()
|
||||
{
|
||||
for (const auto &part: partMap) {
|
||||
for (const auto& part : partMap) {
|
||||
setPartLockState(part.first, false);
|
||||
}
|
||||
}
|
||||
|
@ -990,7 +988,7 @@ void SkeletonDocument::hideDescendantComponents(dust3d::Uuid componentId)
|
|||
{
|
||||
std::vector<dust3d::Uuid> partIds;
|
||||
collectComponentDescendantParts(componentId, partIds);
|
||||
for (const auto &partId: partIds) {
|
||||
for (const auto& partId : partIds) {
|
||||
setPartVisibleState(partId, false);
|
||||
}
|
||||
}
|
||||
|
@ -999,7 +997,7 @@ void SkeletonDocument::showDescendantComponents(dust3d::Uuid componentId)
|
|||
{
|
||||
std::vector<dust3d::Uuid> partIds;
|
||||
collectComponentDescendantParts(componentId, partIds);
|
||||
for (const auto &partId: partIds) {
|
||||
for (const auto& partId : partIds) {
|
||||
setPartVisibleState(partId, true);
|
||||
}
|
||||
}
|
||||
|
@ -1008,7 +1006,7 @@ void SkeletonDocument::lockDescendantComponents(dust3d::Uuid componentId)
|
|||
{
|
||||
std::vector<dust3d::Uuid> partIds;
|
||||
collectComponentDescendantParts(componentId, partIds);
|
||||
for (const auto &partId: partIds) {
|
||||
for (const auto& partId : partIds) {
|
||||
setPartLockState(partId, true);
|
||||
}
|
||||
}
|
||||
|
@ -1017,7 +1015,7 @@ void SkeletonDocument::unlockDescendantComponents(dust3d::Uuid componentId)
|
|||
{
|
||||
std::vector<dust3d::Uuid> partIds;
|
||||
collectComponentDescendantParts(componentId, partIds);
|
||||
for (const auto &partId: partIds) {
|
||||
for (const auto& partId : partIds) {
|
||||
setPartLockState(partId, false);
|
||||
}
|
||||
}
|
||||
|
@ -1042,7 +1040,7 @@ void SkeletonDocument::scaleNodeByAddRadius(dust3d::Uuid nodeId, float amount)
|
|||
|
||||
bool SkeletonDocument::isPartReadonly(dust3d::Uuid partId) const
|
||||
{
|
||||
const SkeletonPart *part = findPart(partId);
|
||||
const SkeletonPart* part = findPart(partId);
|
||||
if (nullptr == part) {
|
||||
return true;
|
||||
}
|
||||
|
@ -1151,7 +1149,7 @@ void SkeletonDocument::switchNodeXZ(dust3d::Uuid nodeId)
|
|||
emit skeletonChanged();
|
||||
}
|
||||
|
||||
const SkeletonComponent *SkeletonDocument::findComponent(dust3d::Uuid componentId) const
|
||||
const SkeletonComponent* SkeletonDocument::findComponent(dust3d::Uuid componentId) const
|
||||
{
|
||||
if (componentId.isNull())
|
||||
return &rootComponent;
|
||||
|
@ -1167,8 +1165,8 @@ void SkeletonDocument::addEdge(dust3d::Uuid fromNodeId, dust3d::Uuid toNodeId)
|
|||
return;
|
||||
}
|
||||
|
||||
const SkeletonNode *fromNode = nullptr;
|
||||
const SkeletonNode *toNode = nullptr;
|
||||
const SkeletonNode* fromNode = nullptr;
|
||||
const SkeletonNode* toNode = nullptr;
|
||||
bool toPartRemoved = false;
|
||||
|
||||
fromNode = findNode(fromNodeId);
|
||||
|
@ -1239,21 +1237,21 @@ void SkeletonDocument::addEdge(dust3d::Uuid fromNodeId, dust3d::Uuid toNodeId)
|
|||
|
||||
void SkeletonDocument::updateLinkedPart(dust3d::Uuid oldPartId, dust3d::Uuid newPartId)
|
||||
{
|
||||
for (auto &partIt: partMap) {
|
||||
for (auto& partIt : partMap) {
|
||||
if (partIt.second.cutFaceLinkedId == oldPartId) {
|
||||
partIt.second.dirty = true;
|
||||
partIt.second.setCutFaceLinkedId(newPartId);
|
||||
}
|
||||
}
|
||||
std::set<dust3d::Uuid> dirtyPartIds;
|
||||
for (auto &nodeIt: nodeMap) {
|
||||
for (auto& nodeIt : nodeMap) {
|
||||
if (nodeIt.second.cutFaceLinkedId == oldPartId) {
|
||||
dirtyPartIds.insert(nodeIt.second.partId);
|
||||
nodeIt.second.setCutFaceLinkedId(newPartId);
|
||||
}
|
||||
}
|
||||
for (const auto &partId: dirtyPartIds) {
|
||||
SkeletonPart *part = (SkeletonPart *)findPart(partId);
|
||||
for (const auto& partId : dirtyPartIds) {
|
||||
SkeletonPart* part = (SkeletonPart*)findPart(partId);
|
||||
if (nullptr == part)
|
||||
continue;
|
||||
part->dirty = true;
|
||||
|
@ -1272,17 +1270,17 @@ void SkeletonDocument::disableAllPositionRelatedLocks()
|
|||
|
||||
void SkeletonDocument::resetDirtyFlags()
|
||||
{
|
||||
for (auto &part: partMap) {
|
||||
for (auto& part : partMap) {
|
||||
part.second.dirty = false;
|
||||
}
|
||||
for (auto &component: componentMap) {
|
||||
for (auto& component : componentMap) {
|
||||
component.second.dirty = false;
|
||||
}
|
||||
}
|
||||
|
||||
void SkeletonDocument::markAllDirty()
|
||||
{
|
||||
for (auto &part: partMap) {
|
||||
for (auto& part : partMap) {
|
||||
part.second.dirty = true;
|
||||
}
|
||||
}
|
||||
|
@ -1319,27 +1317,27 @@ void SkeletonDocument::setRadiusLockState(bool locked)
|
|||
emit radiusLockStateChanged();
|
||||
}
|
||||
|
||||
void SkeletonDocument::setComponentPreviewImage(const dust3d::Uuid &componentId, std::unique_ptr<QImage> image)
|
||||
void SkeletonDocument::setComponentPreviewImage(const dust3d::Uuid& componentId, std::unique_ptr<QImage> image)
|
||||
{
|
||||
SkeletonComponent *component = (SkeletonComponent *)findComponent(componentId);
|
||||
SkeletonComponent* component = (SkeletonComponent*)findComponent(componentId);
|
||||
if (nullptr == component)
|
||||
return;
|
||||
component->isPreviewImageDecorationObsolete = true;
|
||||
component->previewImage = std::move(image);
|
||||
}
|
||||
|
||||
void SkeletonDocument::setComponentPreviewPixmap(const dust3d::Uuid &componentId, const QPixmap &pixmap)
|
||||
void SkeletonDocument::setComponentPreviewPixmap(const dust3d::Uuid& componentId, const QPixmap& pixmap)
|
||||
{
|
||||
SkeletonComponent *component = (SkeletonComponent *)findComponent(componentId);
|
||||
SkeletonComponent* component = (SkeletonComponent*)findComponent(componentId);
|
||||
if (nullptr == component)
|
||||
return;
|
||||
component->previewPixmap = pixmap;
|
||||
emit componentPreviewPixmapChanged(componentId);
|
||||
}
|
||||
|
||||
void SkeletonDocument::setComponentPreviewMesh(const dust3d::Uuid &componentId, std::unique_ptr<ModelMesh> mesh)
|
||||
void SkeletonDocument::setComponentPreviewMesh(const dust3d::Uuid& componentId, std::unique_ptr<ModelMesh> mesh)
|
||||
{
|
||||
SkeletonComponent *component = (SkeletonComponent *)findComponent(componentId);
|
||||
SkeletonComponent* component = (SkeletonComponent*)findComponent(componentId);
|
||||
if (nullptr == component)
|
||||
return;
|
||||
component->updatePreviewMesh(std::move(mesh));
|
||||
|
|
|
@ -1,35 +1,34 @@
|
|||
#ifndef DUST3D_APPLICATION_SKELETON_DOCUMENT_H_
|
||||
#define DUST3D_APPLICATION_SKELETON_DOCUMENT_H_
|
||||
|
||||
#include <QObject>
|
||||
#include <QString>
|
||||
#include <cmath>
|
||||
#include <QImage>
|
||||
#include <QByteArray>
|
||||
#include <QDebug>
|
||||
#include <QVector3D>
|
||||
#include <QPixmap>
|
||||
#include <dust3d/base/uuid.h>
|
||||
#include <dust3d/base/cut_face.h>
|
||||
#include <dust3d/base/part_target.h>
|
||||
#include <dust3d/base/part_base.h>
|
||||
#include <dust3d/base/combine_mode.h>
|
||||
#include "theme.h"
|
||||
#include "model_mesh.h"
|
||||
#include "debug.h"
|
||||
#include "mesh_generator.h"
|
||||
#include "model_mesh.h"
|
||||
#include "theme.h"
|
||||
#include <QByteArray>
|
||||
#include <QDebug>
|
||||
#include <QImage>
|
||||
#include <QObject>
|
||||
#include <QPixmap>
|
||||
#include <QString>
|
||||
#include <QVector3D>
|
||||
#include <cmath>
|
||||
#include <dust3d/base/combine_mode.h>
|
||||
#include <dust3d/base/cut_face.h>
|
||||
#include <dust3d/base/part_base.h>
|
||||
#include <dust3d/base/part_target.h>
|
||||
#include <dust3d/base/uuid.h>
|
||||
|
||||
class SkeletonNode
|
||||
{
|
||||
class SkeletonNode {
|
||||
public:
|
||||
SkeletonNode(const dust3d::Uuid &withId=dust3d::Uuid()) :
|
||||
radius(0),
|
||||
cutRotation(0.0),
|
||||
cutFace(dust3d::CutFace::Quad),
|
||||
hasCutFaceSettings(false),
|
||||
m_x(0),
|
||||
m_y(0),
|
||||
m_z(0)
|
||||
SkeletonNode(const dust3d::Uuid& withId = dust3d::Uuid())
|
||||
: radius(0)
|
||||
, cutRotation(0.0)
|
||||
, cutFace(dust3d::CutFace::Quad)
|
||||
, hasCutFaceSettings(false)
|
||||
, m_x(0)
|
||||
, m_y(0)
|
||||
, m_z(0)
|
||||
{
|
||||
id = withId.isNull() ? dust3d::Uuid::createUuid() : withId;
|
||||
}
|
||||
|
@ -56,7 +55,7 @@ public:
|
|||
cutFaceLinkedId = dust3d::Uuid();
|
||||
hasCutFaceSettings = true;
|
||||
}
|
||||
void setCutFaceLinkedId(const dust3d::Uuid &linkedId)
|
||||
void setCutFaceLinkedId(const dust3d::Uuid& linkedId)
|
||||
{
|
||||
if (linkedId.isNull()) {
|
||||
clearCutFaceSettings();
|
||||
|
@ -73,21 +72,21 @@ public:
|
|||
cutRotation = 0;
|
||||
hasCutFaceSettings = false;
|
||||
}
|
||||
float getX(bool rotated=false) const
|
||||
float getX(bool rotated = false) const
|
||||
{
|
||||
if (rotated)
|
||||
return m_y;
|
||||
return m_x;
|
||||
}
|
||||
float getY(bool rotated=false) const
|
||||
float getY(bool rotated = false) const
|
||||
{
|
||||
if (rotated)
|
||||
return m_x;
|
||||
return m_y;
|
||||
}
|
||||
float getZ(bool rotated=false) const
|
||||
float getZ(bool rotated = false) const
|
||||
{
|
||||
(void) rotated;
|
||||
(void)rotated;
|
||||
return m_z;
|
||||
}
|
||||
void setX(float x)
|
||||
|
@ -123,16 +122,16 @@ public:
|
|||
dust3d::Uuid cutFaceLinkedId;
|
||||
bool hasCutFaceSettings;
|
||||
std::vector<dust3d::Uuid> edgeIds;
|
||||
|
||||
private:
|
||||
float m_x;
|
||||
float m_y;
|
||||
float m_z;
|
||||
};
|
||||
|
||||
class SkeletonEdge
|
||||
{
|
||||
class SkeletonEdge {
|
||||
public:
|
||||
SkeletonEdge(const dust3d::Uuid &withId=dust3d::Uuid())
|
||||
SkeletonEdge(const dust3d::Uuid& withId = dust3d::Uuid())
|
||||
{
|
||||
id = withId.isNull() ? dust3d::Uuid::createUuid() : withId;
|
||||
}
|
||||
|
@ -148,8 +147,7 @@ public:
|
|||
}
|
||||
};
|
||||
|
||||
class SkeletonPart
|
||||
{
|
||||
class SkeletonPart {
|
||||
public:
|
||||
dust3d::Uuid id;
|
||||
QString name;
|
||||
|
@ -180,30 +178,30 @@ public:
|
|||
float hollowThickness;
|
||||
bool countershaded;
|
||||
bool smooth;
|
||||
SkeletonPart(const dust3d::Uuid &withId=dust3d::Uuid()) :
|
||||
visible(true),
|
||||
locked(false),
|
||||
subdived(false),
|
||||
disabled(false),
|
||||
xMirrored(false),
|
||||
base(dust3d::PartBase::Average),
|
||||
deformThickness(1.0),
|
||||
deformWidth(1.0),
|
||||
deformUnified(false),
|
||||
rounded(false),
|
||||
chamfered(false),
|
||||
color(Qt::white),
|
||||
hasColor(false),
|
||||
dirty(true),
|
||||
cutRotation(0.0),
|
||||
cutFace(dust3d::CutFace::Quad),
|
||||
target(dust3d::PartTarget::Model),
|
||||
colorSolubility(0.0),
|
||||
metalness(0.0),
|
||||
roughness(1.0),
|
||||
hollowThickness(0.0),
|
||||
countershaded(false),
|
||||
smooth(false)
|
||||
SkeletonPart(const dust3d::Uuid& withId = dust3d::Uuid())
|
||||
: visible(true)
|
||||
, locked(false)
|
||||
, subdived(false)
|
||||
, disabled(false)
|
||||
, xMirrored(false)
|
||||
, base(dust3d::PartBase::Average)
|
||||
, deformThickness(1.0)
|
||||
, deformWidth(1.0)
|
||||
, deformUnified(false)
|
||||
, rounded(false)
|
||||
, chamfered(false)
|
||||
, color(Qt::white)
|
||||
, hasColor(false)
|
||||
, dirty(true)
|
||||
, cutRotation(0.0)
|
||||
, cutFace(dust3d::CutFace::Quad)
|
||||
, target(dust3d::PartTarget::Model)
|
||||
, colorSolubility(0.0)
|
||||
, metalness(0.0)
|
||||
, roughness(1.0)
|
||||
, hollowThickness(0.0)
|
||||
, countershaded(false)
|
||||
, smooth(false)
|
||||
{
|
||||
id = withId.isNull() ? dust3d::Uuid::createUuid() : withId;
|
||||
}
|
||||
|
@ -296,7 +294,7 @@ public:
|
|||
cutFace = face;
|
||||
cutFaceLinkedId = dust3d::Uuid();
|
||||
}
|
||||
void setCutFaceLinkedId(const dust3d::Uuid &linkedId)
|
||||
void setCutFaceLinkedId(const dust3d::Uuid& linkedId)
|
||||
{
|
||||
if (linkedId.isNull()) {
|
||||
setCutFace(dust3d::CutFace::Quad);
|
||||
|
@ -353,7 +351,7 @@ public:
|
|||
{
|
||||
return visible && !disabled;
|
||||
}
|
||||
void copyAttributes(const SkeletonPart &other)
|
||||
void copyAttributes(const SkeletonPart& other)
|
||||
{
|
||||
visible = other.visible;
|
||||
locked = other.locked;
|
||||
|
@ -382,12 +380,12 @@ public:
|
|||
smooth = other.smooth;
|
||||
hollowThickness = other.hollowThickness;
|
||||
}
|
||||
|
||||
private:
|
||||
Q_DISABLE_COPY(SkeletonPart);
|
||||
};
|
||||
|
||||
enum class SkeletonDocumentEditMode
|
||||
{
|
||||
enum class SkeletonDocumentEditMode {
|
||||
Add = 0,
|
||||
Select,
|
||||
Paint,
|
||||
|
@ -396,20 +394,18 @@ enum class SkeletonDocumentEditMode
|
|||
ZoomOut
|
||||
};
|
||||
|
||||
enum class SkeletonProfile
|
||||
{
|
||||
enum class SkeletonProfile {
|
||||
Unknown = 0,
|
||||
Main,
|
||||
Side
|
||||
};
|
||||
|
||||
class SkeletonComponent
|
||||
{
|
||||
class SkeletonComponent {
|
||||
public:
|
||||
SkeletonComponent()
|
||||
{
|
||||
}
|
||||
SkeletonComponent(const dust3d::Uuid &withId, const QString &linkData=QString(), const QString &linkDataType=QString())
|
||||
SkeletonComponent(const dust3d::Uuid& withId, const QString& linkData = QString(), const QString& linkDataType = QString())
|
||||
{
|
||||
id = withId.isNull() ? dust3d::Uuid::createUuid() : withId;
|
||||
if (!linkData.isEmpty()) {
|
||||
|
@ -445,13 +441,13 @@ public:
|
|||
m_childrenIdSet.insert(childId);
|
||||
childrenIds.push_back(childId);
|
||||
}
|
||||
void replaceChildWithOthers(const dust3d::Uuid &childId, const std::vector<dust3d::Uuid> &others)
|
||||
void replaceChildWithOthers(const dust3d::Uuid& childId, const std::vector<dust3d::Uuid>& others)
|
||||
{
|
||||
if (m_childrenIdSet.find(childId) == m_childrenIdSet.end())
|
||||
return;
|
||||
m_childrenIdSet.erase(childId);
|
||||
std::vector<dust3d::Uuid> candidates;
|
||||
for (const auto &it: others) {
|
||||
for (const auto& it : others) {
|
||||
if (m_childrenIdSet.find(it) == m_childrenIdSet.end()) {
|
||||
m_childrenIdSet.insert(it);
|
||||
candidates.emplace_back(it);
|
||||
|
@ -549,19 +545,19 @@ public:
|
|||
m_previewMesh = std::move(mesh);
|
||||
isPreviewMeshObsolete = true;
|
||||
}
|
||||
ModelMesh *takePreviewMesh() const
|
||||
ModelMesh* takePreviewMesh() const
|
||||
{
|
||||
if (nullptr == m_previewMesh)
|
||||
return nullptr;
|
||||
return new ModelMesh(*m_previewMesh);
|
||||
}
|
||||
|
||||
private:
|
||||
std::unique_ptr<ModelMesh> m_previewMesh;
|
||||
std::set<dust3d::Uuid> m_childrenIdSet;
|
||||
};
|
||||
|
||||
class SkeletonDocument : public QObject
|
||||
{
|
||||
class SkeletonDocument : public QObject {
|
||||
Q_OBJECT
|
||||
signals:
|
||||
void partAdded(dust3d::Uuid partId);
|
||||
|
@ -576,8 +572,8 @@ signals:
|
|||
void componentRemoved(dust3d::Uuid componentId);
|
||||
void componentAdded(dust3d::Uuid componentId);
|
||||
void componentExpandStateChanged(dust3d::Uuid componentId);
|
||||
void componentPreviewMeshChanged(const dust3d::Uuid &componentId);
|
||||
void componentPreviewPixmapChanged(const dust3d::Uuid &componentId);
|
||||
void componentPreviewMeshChanged(const dust3d::Uuid& componentId);
|
||||
void componentPreviewPixmapChanged(const dust3d::Uuid& componentId);
|
||||
void nodeRemoved(dust3d::Uuid nodeId);
|
||||
void edgeRemoved(dust3d::Uuid edgeId);
|
||||
void nodeRadiusChanged(dust3d::Uuid nodeId);
|
||||
|
@ -590,6 +586,7 @@ signals:
|
|||
void ylockStateChanged();
|
||||
void zlockStateChanged();
|
||||
void radiusLockStateChanged();
|
||||
|
||||
public:
|
||||
SkeletonDocumentEditMode editMode = SkeletonDocumentEditMode::Select;
|
||||
bool xlocked = false;
|
||||
|
@ -604,19 +601,19 @@ public:
|
|||
std::map<dust3d::Uuid, SkeletonComponent> componentMap;
|
||||
SkeletonComponent rootComponent;
|
||||
|
||||
const SkeletonNode *findNode(dust3d::Uuid nodeId) const;
|
||||
const SkeletonEdge *findEdge(dust3d::Uuid edgeId) const;
|
||||
const SkeletonPart *findPart(dust3d::Uuid partId) const;
|
||||
const SkeletonEdge *findEdgeByNodes(dust3d::Uuid firstNodeId, dust3d::Uuid secondNodeId) const;
|
||||
void findAllNeighbors(dust3d::Uuid nodeId, std::set<dust3d::Uuid> &neighbors) const;
|
||||
const SkeletonNode* findNode(dust3d::Uuid nodeId) const;
|
||||
const SkeletonEdge* findEdge(dust3d::Uuid edgeId) const;
|
||||
const SkeletonPart* findPart(dust3d::Uuid partId) const;
|
||||
const SkeletonEdge* findEdgeByNodes(dust3d::Uuid firstNodeId, dust3d::Uuid secondNodeId) const;
|
||||
void findAllNeighbors(dust3d::Uuid nodeId, std::set<dust3d::Uuid>& neighbors) const;
|
||||
bool isNodeConnectable(dust3d::Uuid nodeId) const;
|
||||
const SkeletonComponent *findComponent(dust3d::Uuid componentId) const;
|
||||
const SkeletonComponent *findComponentParent(dust3d::Uuid componentId) const;
|
||||
const SkeletonComponent* findComponent(dust3d::Uuid componentId) const;
|
||||
const SkeletonComponent* findComponentParent(dust3d::Uuid componentId) const;
|
||||
dust3d::Uuid findComponentParentId(dust3d::Uuid componentId) const;
|
||||
void collectComponentDescendantParts(dust3d::Uuid componentId, std::vector<dust3d::Uuid> &partIds) const;
|
||||
void collectComponentDescendantComponents(dust3d::Uuid componentId, std::vector<dust3d::Uuid> &componentIds) const;
|
||||
void setComponentPreviewMesh(const dust3d::Uuid &componentId, std::unique_ptr<ModelMesh> mesh);
|
||||
void setComponentPreviewImage(const dust3d::Uuid &componentId, std::unique_ptr<QImage> image);
|
||||
void collectComponentDescendantParts(dust3d::Uuid componentId, std::vector<dust3d::Uuid>& partIds) const;
|
||||
void collectComponentDescendantComponents(dust3d::Uuid componentId, std::vector<dust3d::Uuid>& componentIds) const;
|
||||
void setComponentPreviewMesh(const dust3d::Uuid& componentId, std::unique_ptr<ModelMesh> mesh);
|
||||
void setComponentPreviewImage(const dust3d::Uuid& componentId, std::unique_ptr<QImage> image);
|
||||
void resetDirtyFlags();
|
||||
void markAllDirty();
|
||||
|
||||
|
@ -628,31 +625,31 @@ public:
|
|||
virtual bool isEdgeEditable(dust3d::Uuid edgeId) const = 0;
|
||||
virtual bool isNodeDeactivated(dust3d::Uuid nodeId) const
|
||||
{
|
||||
(void) nodeId;
|
||||
(void)nodeId;
|
||||
return false;
|
||||
};
|
||||
virtual bool isEdgeDeactivated(dust3d::Uuid edgeId) const
|
||||
{
|
||||
(void) edgeId;
|
||||
(void)edgeId;
|
||||
return false;
|
||||
};
|
||||
virtual void copyNodes(std::set<dust3d::Uuid> nodeIdSet) const = 0;
|
||||
|
||||
float getOriginX(bool rotated=false) const
|
||||
float getOriginX(bool rotated = false) const
|
||||
{
|
||||
if (rotated)
|
||||
return m_originY;
|
||||
return m_originX;
|
||||
}
|
||||
float getOriginY(bool rotated=false) const
|
||||
float getOriginY(bool rotated = false) const
|
||||
{
|
||||
if (rotated)
|
||||
return m_originX;
|
||||
return m_originY;
|
||||
}
|
||||
float getOriginZ(bool rotated=false) const
|
||||
float getOriginZ(bool rotated = false) const
|
||||
{
|
||||
(void) rotated;
|
||||
(void)rotated;
|
||||
return m_originZ;
|
||||
}
|
||||
void setOriginX(float originX)
|
||||
|
@ -706,8 +703,8 @@ public slots:
|
|||
void addComponent(dust3d::Uuid parentId);
|
||||
void moveComponent(dust3d::Uuid componentId, dust3d::Uuid toParentId);
|
||||
void setCurrentCanvasComponentId(dust3d::Uuid componentId);
|
||||
void groupComponents(const std::vector<dust3d::Uuid> &componentIds);
|
||||
void ungroupComponent(const dust3d::Uuid &componentId);
|
||||
void groupComponents(const std::vector<dust3d::Uuid>& componentIds);
|
||||
void ungroupComponent(const dust3d::Uuid& componentId);
|
||||
void createNewChildComponent(dust3d::Uuid parentComponentId);
|
||||
void setComponentExpandState(dust3d::Uuid componentId, bool expanded);
|
||||
void hideOtherComponents(dust3d::Uuid componentId);
|
||||
|
@ -723,7 +720,7 @@ public slots:
|
|||
void showDescendantComponents(dust3d::Uuid componentId);
|
||||
void lockDescendantComponents(dust3d::Uuid componentId);
|
||||
void unlockDescendantComponents(dust3d::Uuid componentId);
|
||||
void setComponentPreviewPixmap(const dust3d::Uuid &componentId, const QPixmap &pixmap);
|
||||
void setComponentPreviewPixmap(const dust3d::Uuid& componentId, const QPixmap& pixmap);
|
||||
void setPartLockState(dust3d::Uuid partId, bool locked);
|
||||
void setPartVisibleState(dust3d::Uuid partId, bool visible);
|
||||
void setPartDisableState(dust3d::Uuid partId, bool disabled);
|
||||
|
@ -746,9 +743,9 @@ private:
|
|||
dust3d::Uuid m_currentCanvasComponentId;
|
||||
bool m_allPositionRelatedLocksEnabled = true;
|
||||
|
||||
void splitPartByNode(std::vector<std::vector<dust3d::Uuid>> *groups, dust3d::Uuid nodeId);
|
||||
void joinNodeAndNeiborsToGroup(std::vector<dust3d::Uuid> *group, dust3d::Uuid nodeId, std::set<dust3d::Uuid> *visitMap, dust3d::Uuid noUseEdgeId=dust3d::Uuid());
|
||||
void splitPartByEdge(std::vector<std::vector<dust3d::Uuid>> *groups, dust3d::Uuid edgeId);
|
||||
void splitPartByNode(std::vector<std::vector<dust3d::Uuid>>* groups, dust3d::Uuid nodeId);
|
||||
void joinNodeAndNeiborsToGroup(std::vector<dust3d::Uuid>* group, dust3d::Uuid nodeId, std::set<dust3d::Uuid>* visitMap, dust3d::Uuid noUseEdgeId = dust3d::Uuid());
|
||||
void splitPartByEdge(std::vector<std::vector<dust3d::Uuid>>* groups, dust3d::Uuid edgeId);
|
||||
void removePartDontCareComponent(dust3d::Uuid partId);
|
||||
void addPartToComponent(dust3d::Uuid partId, dust3d::Uuid componentId);
|
||||
bool isDescendantComponent(dust3d::Uuid componentId, dust3d::Uuid suspiciousId);
|
||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -1,32 +1,31 @@
|
|||
#ifndef DUST3D_APPLICATION_SKELETON_GRAPHICS_VIEW_H_
|
||||
#define DUST3D_APPLICATION_SKELETON_GRAPHICS_VIEW_H_
|
||||
|
||||
#include <map>
|
||||
#include <QMouseEvent>
|
||||
#include <QKeyEvent>
|
||||
#include "model_widget.h"
|
||||
#include "skeleton_document.h"
|
||||
#include "skeleton_ik_mover.h"
|
||||
#include "theme.h"
|
||||
#include "turnaround_loader.h"
|
||||
#include <QGraphicsEllipseItem>
|
||||
#include <QGraphicsLineItem>
|
||||
#include <QGraphicsView>
|
||||
#include <QGraphicsPixmapItem>
|
||||
#include <QGraphicsPolygonItem>
|
||||
#include <QGraphicsView>
|
||||
#include <QKeyEvent>
|
||||
#include <QMouseEvent>
|
||||
#include <QThread>
|
||||
#include <cmath>
|
||||
#include <set>
|
||||
#include <QTimer>
|
||||
#include "skeleton_document.h"
|
||||
#include "turnaround_loader.h"
|
||||
#include "theme.h"
|
||||
#include "skeleton_ik_mover.h"
|
||||
#include "model_widget.h"
|
||||
#include <cmath>
|
||||
#include <map>
|
||||
#include <set>
|
||||
|
||||
class SkeletonGraphicsOriginItem : public QGraphicsPolygonItem
|
||||
{
|
||||
class SkeletonGraphicsOriginItem : public QGraphicsPolygonItem {
|
||||
public:
|
||||
SkeletonGraphicsOriginItem(SkeletonProfile profile=SkeletonProfile::Unknown) :
|
||||
m_profile(profile),
|
||||
m_hovered(false),
|
||||
m_checked(false),
|
||||
m_rotated(false)
|
||||
SkeletonGraphicsOriginItem(SkeletonProfile profile = SkeletonProfile::Unknown)
|
||||
: m_profile(profile)
|
||||
, m_hovered(false)
|
||||
, m_checked(false)
|
||||
, m_rotated(false)
|
||||
{
|
||||
setData(0, "origin");
|
||||
}
|
||||
|
@ -38,8 +37,7 @@ public:
|
|||
{
|
||||
QColor color = Theme::white;
|
||||
|
||||
switch (m_profile)
|
||||
{
|
||||
switch (m_profile) {
|
||||
case SkeletonProfile::Unknown:
|
||||
break;
|
||||
case SkeletonProfile::Main:
|
||||
|
@ -99,6 +97,7 @@ public:
|
|||
{
|
||||
return m_hovered;
|
||||
}
|
||||
|
||||
private:
|
||||
SkeletonProfile m_profile;
|
||||
bool m_hovered;
|
||||
|
@ -107,8 +106,7 @@ private:
|
|||
bool m_rotated;
|
||||
};
|
||||
|
||||
class SkeletonGraphicsSelectionItem : public QGraphicsRectItem
|
||||
{
|
||||
class SkeletonGraphicsSelectionItem : public QGraphicsRectItem {
|
||||
public:
|
||||
SkeletonGraphicsSelectionItem()
|
||||
{
|
||||
|
@ -124,16 +122,15 @@ public:
|
|||
}
|
||||
};
|
||||
|
||||
class SkeletonGraphicsNodeItem : public QGraphicsEllipseItem
|
||||
{
|
||||
class SkeletonGraphicsNodeItem : public QGraphicsEllipseItem {
|
||||
public:
|
||||
SkeletonGraphicsNodeItem(SkeletonProfile profile=SkeletonProfile::Unknown) :
|
||||
m_profile(profile),
|
||||
m_hovered(false),
|
||||
m_checked(false),
|
||||
m_markColor(Qt::transparent),
|
||||
m_deactivated(false),
|
||||
m_rotated(false)
|
||||
SkeletonGraphicsNodeItem(SkeletonProfile profile = SkeletonProfile::Unknown)
|
||||
: m_profile(profile)
|
||||
, m_hovered(false)
|
||||
, m_checked(false)
|
||||
, m_markColor(Qt::transparent)
|
||||
, m_deactivated(false)
|
||||
, m_rotated(false)
|
||||
{
|
||||
setData(0, "node");
|
||||
setRadius(32);
|
||||
|
@ -147,8 +144,7 @@ public:
|
|||
QColor color = Qt::gray;
|
||||
|
||||
if (!m_deactivated) {
|
||||
switch (m_profile)
|
||||
{
|
||||
switch (m_profile) {
|
||||
case SkeletonProfile::Unknown:
|
||||
break;
|
||||
case SkeletonProfile::Main:
|
||||
|
@ -253,6 +249,7 @@ public:
|
|||
{
|
||||
return m_hovered;
|
||||
}
|
||||
|
||||
private:
|
||||
dust3d::Uuid m_uuid;
|
||||
SkeletonProfile m_profile;
|
||||
|
@ -263,17 +260,16 @@ private:
|
|||
bool m_rotated;
|
||||
};
|
||||
|
||||
class SkeletonGraphicsEdgeItem : public QGraphicsPolygonItem
|
||||
{
|
||||
class SkeletonGraphicsEdgeItem : public QGraphicsPolygonItem {
|
||||
public:
|
||||
SkeletonGraphicsEdgeItem() :
|
||||
m_firstItem(nullptr),
|
||||
m_secondItem(nullptr),
|
||||
m_hovered(false),
|
||||
m_checked(false),
|
||||
m_profile(SkeletonProfile::Unknown),
|
||||
m_deactivated(false),
|
||||
m_rotated(false)
|
||||
SkeletonGraphicsEdgeItem()
|
||||
: m_firstItem(nullptr)
|
||||
, m_secondItem(nullptr)
|
||||
, m_hovered(false)
|
||||
, m_checked(false)
|
||||
, m_profile(SkeletonProfile::Unknown)
|
||||
, m_deactivated(false)
|
||||
, m_rotated(false)
|
||||
{
|
||||
setData(0, "edge");
|
||||
}
|
||||
|
@ -281,17 +277,17 @@ public:
|
|||
{
|
||||
m_rotated = rotated;
|
||||
}
|
||||
void setEndpoints(SkeletonGraphicsNodeItem *first, SkeletonGraphicsNodeItem *second)
|
||||
void setEndpoints(SkeletonGraphicsNodeItem* first, SkeletonGraphicsNodeItem* second)
|
||||
{
|
||||
m_firstItem = first;
|
||||
m_secondItem = second;
|
||||
updateAppearance();
|
||||
}
|
||||
SkeletonGraphicsNodeItem *firstItem()
|
||||
SkeletonGraphicsNodeItem* firstItem()
|
||||
{
|
||||
return m_firstItem;
|
||||
}
|
||||
SkeletonGraphicsNodeItem *secondItem()
|
||||
SkeletonGraphicsNodeItem* secondItem()
|
||||
{
|
||||
return m_secondItem;
|
||||
}
|
||||
|
@ -317,8 +313,7 @@ public:
|
|||
QColor color = Qt::gray;
|
||||
|
||||
if (!m_deactivated) {
|
||||
switch (m_firstItem->profile())
|
||||
{
|
||||
switch (m_firstItem->profile()) {
|
||||
case SkeletonProfile::Unknown:
|
||||
break;
|
||||
case SkeletonProfile::Main:
|
||||
|
@ -380,10 +375,11 @@ public:
|
|||
{
|
||||
return m_hovered;
|
||||
}
|
||||
|
||||
private:
|
||||
dust3d::Uuid m_uuid;
|
||||
SkeletonGraphicsNodeItem *m_firstItem;
|
||||
SkeletonGraphicsNodeItem *m_secondItem;
|
||||
SkeletonGraphicsNodeItem* m_firstItem;
|
||||
SkeletonGraphicsNodeItem* m_secondItem;
|
||||
QPolygonF m_selectionPolygon;
|
||||
bool m_hovered;
|
||||
bool m_checked;
|
||||
|
@ -392,8 +388,7 @@ private:
|
|||
bool m_rotated;
|
||||
};
|
||||
|
||||
class SkeletonGraphicsWidget : public QGraphicsView
|
||||
{
|
||||
class SkeletonGraphicsWidget : public QGraphicsView {
|
||||
Q_OBJECT
|
||||
public:
|
||||
~SkeletonGraphicsWidget();
|
||||
|
@ -445,43 +440,45 @@ signals:
|
|||
void shortcutToggleFlatShading();
|
||||
void shortcutToggleRotation();
|
||||
void loadedTurnaroundImageChanged();
|
||||
|
||||
public:
|
||||
SkeletonGraphicsWidget(const SkeletonDocument *document);
|
||||
std::map<dust3d::Uuid, std::pair<SkeletonGraphicsNodeItem *, SkeletonGraphicsNodeItem *>> nodeItemMap;
|
||||
std::map<dust3d::Uuid, std::pair<SkeletonGraphicsEdgeItem *, SkeletonGraphicsEdgeItem *>> edgeItemMap;
|
||||
bool mouseMove(QMouseEvent *event);
|
||||
bool wheel(QWheelEvent *event);
|
||||
bool mouseRelease(QMouseEvent *event);
|
||||
bool mousePress(QMouseEvent *event);
|
||||
bool mouseDoubleClick(QMouseEvent *event);
|
||||
bool keyPress(QKeyEvent *event);
|
||||
bool keyRelease(QKeyEvent *event);
|
||||
bool checkSkeletonItem(QGraphicsItem *item, bool checked);
|
||||
dust3d::Uuid querySkeletonItemPartId(QGraphicsItem *item);
|
||||
static SkeletonProfile readSkeletonItemProfile(QGraphicsItem *item);
|
||||
void getOtherProfileNodeItems(const std::set<SkeletonGraphicsNodeItem *> &nodeItemSet,
|
||||
std::set<SkeletonGraphicsNodeItem *> *otherProfileNodeItemSet);
|
||||
void readMergedSkeletonNodeSetFromRangeSelection(std::set<SkeletonGraphicsNodeItem *> *nodeItemSet);
|
||||
void readSkeletonNodeAndEdgeIdSetFromRangeSelection(std::set<dust3d::Uuid> *nodeIdSet, std::set<dust3d::Uuid> *edgeIdSet=nullptr);
|
||||
bool readSkeletonNodeAndAnyEdgeOfNodeFromRangeSelection(SkeletonGraphicsNodeItem **nodeItem, SkeletonGraphicsEdgeItem **edgeItem);
|
||||
SkeletonGraphicsWidget(const SkeletonDocument* document);
|
||||
std::map<dust3d::Uuid, std::pair<SkeletonGraphicsNodeItem*, SkeletonGraphicsNodeItem*>> nodeItemMap;
|
||||
std::map<dust3d::Uuid, std::pair<SkeletonGraphicsEdgeItem*, SkeletonGraphicsEdgeItem*>> edgeItemMap;
|
||||
bool mouseMove(QMouseEvent* event);
|
||||
bool wheel(QWheelEvent* event);
|
||||
bool mouseRelease(QMouseEvent* event);
|
||||
bool mousePress(QMouseEvent* event);
|
||||
bool mouseDoubleClick(QMouseEvent* event);
|
||||
bool keyPress(QKeyEvent* event);
|
||||
bool keyRelease(QKeyEvent* event);
|
||||
bool checkSkeletonItem(QGraphicsItem* item, bool checked);
|
||||
dust3d::Uuid querySkeletonItemPartId(QGraphicsItem* item);
|
||||
static SkeletonProfile readSkeletonItemProfile(QGraphicsItem* item);
|
||||
void getOtherProfileNodeItems(const std::set<SkeletonGraphicsNodeItem*>& nodeItemSet,
|
||||
std::set<SkeletonGraphicsNodeItem*>* otherProfileNodeItemSet);
|
||||
void readMergedSkeletonNodeSetFromRangeSelection(std::set<SkeletonGraphicsNodeItem*>* nodeItemSet);
|
||||
void readSkeletonNodeAndEdgeIdSetFromRangeSelection(std::set<dust3d::Uuid>* nodeIdSet, std::set<dust3d::Uuid>* edgeIdSet = nullptr);
|
||||
bool readSkeletonNodeAndAnyEdgeOfNodeFromRangeSelection(SkeletonGraphicsNodeItem** nodeItem, SkeletonGraphicsEdgeItem** edgeItem);
|
||||
bool hasSelection();
|
||||
bool hasItems();
|
||||
bool hasMultipleSelection();
|
||||
bool hasEdgeSelection();
|
||||
bool hasNodeSelection();
|
||||
bool hasTwoDisconnectedNodesSelection();
|
||||
void setModelWidget(ModelWidget *modelWidget);
|
||||
bool inputWheelEventFromOtherWidget(QWheelEvent *event);
|
||||
void setModelWidget(ModelWidget* modelWidget);
|
||||
bool inputWheelEventFromOtherWidget(QWheelEvent* event);
|
||||
bool rotated();
|
||||
const QImage *loadedTurnaroundImage() const;
|
||||
const QImage* loadedTurnaroundImage() const;
|
||||
|
||||
protected:
|
||||
void mouseMoveEvent(QMouseEvent *event) override;
|
||||
void wheelEvent(QWheelEvent *event) override;
|
||||
void mouseReleaseEvent(QMouseEvent *event) override;
|
||||
void mousePressEvent(QMouseEvent *event) override;
|
||||
void mouseDoubleClickEvent(QMouseEvent *event) override;
|
||||
void keyPressEvent(QKeyEvent *event) override;
|
||||
void keyReleaseEvent(QKeyEvent *event) override;
|
||||
void mouseMoveEvent(QMouseEvent* event) override;
|
||||
void wheelEvent(QWheelEvent* event) override;
|
||||
void mouseReleaseEvent(QMouseEvent* event) override;
|
||||
void mousePressEvent(QMouseEvent* event) override;
|
||||
void mouseDoubleClickEvent(QMouseEvent* event) override;
|
||||
void keyPressEvent(QKeyEvent* event) override;
|
||||
void keyReleaseEvent(QKeyEvent* event) override;
|
||||
public slots:
|
||||
void nodeAdded(dust3d::Uuid nodeId);
|
||||
void edgeAdded(dust3d::Uuid edgeId);
|
||||
|
@ -495,7 +492,7 @@ public slots:
|
|||
void editModeChanged();
|
||||
void updateCursor();
|
||||
void partVisibleStateChanged(dust3d::Uuid partId);
|
||||
void showContextMenu(const QPoint &pos);
|
||||
void showContextMenu(const QPoint& pos);
|
||||
void deleteSelected();
|
||||
void selectAll();
|
||||
void unselectAll();
|
||||
|
@ -577,8 +574,9 @@ public slots:
|
|||
void shortcutEscape();
|
||||
private slots:
|
||||
void turnaroundImageReady();
|
||||
|
||||
private:
|
||||
QPointF mouseEventScenePos(QMouseEvent *event);
|
||||
QPointF mouseEventScenePos(QMouseEvent* event);
|
||||
QPointF scenePosToUnified(QPointF pos);
|
||||
QPointF scenePosFromUnified(QPointF pos);
|
||||
float sceneRadiusToUnified(float radius);
|
||||
|
@ -587,56 +585,57 @@ private:
|
|||
void updateItems();
|
||||
void checkRangeSelection();
|
||||
void clearRangeSelection();
|
||||
void removeItem(QGraphicsItem *item);
|
||||
QVector2D centerOfNodeItemSet(const std::set<SkeletonGraphicsNodeItem *> &set);
|
||||
void removeItem(QGraphicsItem* item);
|
||||
QVector2D centerOfNodeItemSet(const std::set<SkeletonGraphicsNodeItem*>& set);
|
||||
bool isSingleNodeSelected();
|
||||
void addItemToRangeSelection(QGraphicsItem *item);
|
||||
void removeItemFromRangeSelection(QGraphicsItem *item);
|
||||
void addItemToRangeSelection(QGraphicsItem* item);
|
||||
void removeItemFromRangeSelection(QGraphicsItem* item);
|
||||
void hoverPart(dust3d::Uuid partId);
|
||||
void switchProfileOnRangeSelection();
|
||||
void setItemHoveredOnAllProfiles(QGraphicsItem *item, bool hovered);
|
||||
void setItemHoveredOnAllProfiles(QGraphicsItem* item, bool hovered);
|
||||
void alignSelectedToGlobal(bool alignToVerticalCenter, bool alignToHorizontalCenter);
|
||||
void alignSelectedToLocal(bool alignToVerticalCenter, bool alignToHorizontalCenter);
|
||||
void rotateItems(const std::set<SkeletonGraphicsNodeItem *> &nodeItems, int degree, QVector2D center);
|
||||
void rotateItems(const std::set<SkeletonGraphicsNodeItem*>& nodeItems, int degree, QVector2D center);
|
||||
void rotateAllSideProfile(int degree);
|
||||
bool isFloatEqual(float a, float b);
|
||||
|
||||
private:
|
||||
const SkeletonDocument *m_document = nullptr;
|
||||
QGraphicsPixmapItem *m_backgroundItem = nullptr;
|
||||
const SkeletonDocument* m_document = nullptr;
|
||||
QGraphicsPixmapItem* m_backgroundItem = nullptr;
|
||||
bool m_turnaroundChanged = false;
|
||||
TurnaroundLoader *m_turnaroundLoader = nullptr;
|
||||
TurnaroundLoader* m_turnaroundLoader = nullptr;
|
||||
bool m_dragStarted = false;
|
||||
bool m_moveStarted = false;
|
||||
SkeletonGraphicsNodeItem *m_cursorNodeItem = nullptr;
|
||||
SkeletonGraphicsEdgeItem *m_cursorEdgeItem = nullptr;
|
||||
SkeletonGraphicsNodeItem *m_addFromNodeItem = nullptr;
|
||||
SkeletonGraphicsNodeItem *m_hoveredNodeItem = nullptr;
|
||||
SkeletonGraphicsEdgeItem *m_hoveredEdgeItem = nullptr;
|
||||
SkeletonGraphicsNodeItem* m_cursorNodeItem = nullptr;
|
||||
SkeletonGraphicsEdgeItem* m_cursorEdgeItem = nullptr;
|
||||
SkeletonGraphicsNodeItem* m_addFromNodeItem = nullptr;
|
||||
SkeletonGraphicsNodeItem* m_hoveredNodeItem = nullptr;
|
||||
SkeletonGraphicsEdgeItem* m_hoveredEdgeItem = nullptr;
|
||||
float m_lastAddedX = false;
|
||||
float m_lastAddedY = false;
|
||||
float m_lastAddedZ = false;
|
||||
SkeletonGraphicsSelectionItem *m_selectionItem = nullptr;
|
||||
SkeletonGraphicsSelectionItem* m_selectionItem = nullptr;
|
||||
bool m_rangeSelectionStarted = false;
|
||||
bool m_mouseEventFromSelf = false;
|
||||
bool m_moveHappened = false;
|
||||
int m_lastRot = 0;
|
||||
SkeletonGraphicsOriginItem *m_mainOriginItem = nullptr;
|
||||
SkeletonGraphicsOriginItem *m_sideOriginItem = nullptr;
|
||||
SkeletonGraphicsOriginItem *m_hoveredOriginItem = nullptr;
|
||||
SkeletonGraphicsOriginItem *m_checkedOriginItem = nullptr;
|
||||
SkeletonGraphicsOriginItem* m_mainOriginItem = nullptr;
|
||||
SkeletonGraphicsOriginItem* m_sideOriginItem = nullptr;
|
||||
SkeletonGraphicsOriginItem* m_hoveredOriginItem = nullptr;
|
||||
SkeletonGraphicsOriginItem* m_checkedOriginItem = nullptr;
|
||||
unsigned long long m_ikMoveUpdateVersion = 0;
|
||||
SkeletonIkMover *m_ikMover = nullptr;
|
||||
QTimer *m_deferredRemoveTimer = nullptr;
|
||||
SkeletonIkMover* m_ikMover = nullptr;
|
||||
QTimer* m_deferredRemoveTimer = nullptr;
|
||||
bool m_eventForwardingToModelWidget = false;
|
||||
ModelWidget *m_modelWidget = nullptr;
|
||||
ModelWidget* m_modelWidget = nullptr;
|
||||
bool m_inTempDragMode = false;
|
||||
SkeletonDocumentEditMode m_modeBeforeEnterTempDragMode = SkeletonDocumentEditMode::Select;
|
||||
float m_turnaroundOpacity = 0.25f;
|
||||
bool m_rotated = false;
|
||||
QImage *m_backgroundImage = nullptr;
|
||||
QImage* m_backgroundImage = nullptr;
|
||||
QVector3D m_ikMoveTarget;
|
||||
dust3d::Uuid m_ikMoveEndEffectorId;
|
||||
std::set<QGraphicsItem *> m_rangeSelectionSet;
|
||||
std::set<QGraphicsItem*> m_rangeSelectionSet;
|
||||
QPoint m_lastGlobalPos;
|
||||
QPointF m_lastScenePos;
|
||||
QPointF m_rangeSelectionStartPos;
|
||||
|
@ -645,27 +644,28 @@ private:
|
|||
std::set<dust3d::Uuid> m_deferredRemoveEdgeIds;
|
||||
};
|
||||
|
||||
class SkeletonGraphicsContainerWidget : public QWidget
|
||||
{
|
||||
class SkeletonGraphicsContainerWidget : public QWidget {
|
||||
Q_OBJECT
|
||||
signals:
|
||||
void containerSizeChanged(QSize size);
|
||||
|
||||
public:
|
||||
SkeletonGraphicsContainerWidget() :
|
||||
m_graphicsWidget(nullptr)
|
||||
SkeletonGraphicsContainerWidget()
|
||||
: m_graphicsWidget(nullptr)
|
||||
{
|
||||
}
|
||||
void resizeEvent(QResizeEvent *event) override
|
||||
void resizeEvent(QResizeEvent* event) override
|
||||
{
|
||||
if (m_graphicsWidget && m_graphicsWidget->size() != event->size())
|
||||
emit containerSizeChanged(event->size());
|
||||
}
|
||||
void setGraphicsWidget(SkeletonGraphicsWidget *graphicsWidget)
|
||||
void setGraphicsWidget(SkeletonGraphicsWidget* graphicsWidget)
|
||||
{
|
||||
m_graphicsWidget = graphicsWidget;
|
||||
}
|
||||
|
||||
private:
|
||||
SkeletonGraphicsWidget *m_graphicsWidget;
|
||||
SkeletonGraphicsWidget* m_graphicsWidget;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
#include <QGuiApplication>
|
||||
#include "skeleton_ik_mover.h"
|
||||
#include "ccd_ik_resolver.h"
|
||||
#include <QGuiApplication>
|
||||
|
||||
SkeletonIkMover::SkeletonIkMover()
|
||||
{
|
||||
|
@ -10,7 +10,7 @@ SkeletonIkMover::~SkeletonIkMover()
|
|||
{
|
||||
}
|
||||
|
||||
void SkeletonIkMover::setTarget(const QVector3D &target)
|
||||
void SkeletonIkMover::setTarget(const QVector3D& target)
|
||||
{
|
||||
m_target = target;
|
||||
}
|
||||
|
@ -33,7 +33,7 @@ void SkeletonIkMover::addNode(dust3d::Uuid id, QVector3D position)
|
|||
m_ikNodes.push_back(ikNode);
|
||||
}
|
||||
|
||||
const std::vector<SkeletonIkNode> &SkeletonIkMover::ikNodes()
|
||||
const std::vector<SkeletonIkNode>& SkeletonIkMover::ikNodes()
|
||||
{
|
||||
return m_ikNodes;
|
||||
}
|
||||
|
|
|
@ -2,34 +2,34 @@
|
|||
#define DUST3D_APPLICATION_SKELETON_IK_MOVER_H_
|
||||
|
||||
#include <QObject>
|
||||
#include <vector>
|
||||
#include <QVector3D>
|
||||
#include <dust3d/base/uuid.h>
|
||||
#include <vector>
|
||||
|
||||
struct SkeletonIkNode
|
||||
{
|
||||
struct SkeletonIkNode {
|
||||
dust3d::Uuid id;
|
||||
QVector3D position;
|
||||
QVector3D newPosition;
|
||||
};
|
||||
|
||||
class SkeletonIkMover : public QObject
|
||||
{
|
||||
class SkeletonIkMover : public QObject {
|
||||
Q_OBJECT
|
||||
public:
|
||||
SkeletonIkMover();
|
||||
~SkeletonIkMover();
|
||||
void setTarget(const QVector3D &target);
|
||||
void setTarget(const QVector3D& target);
|
||||
void setUpdateVersion(unsigned long long version);
|
||||
unsigned long long getUpdateVersion();
|
||||
void addNode(dust3d::Uuid id, QVector3D position);
|
||||
const std::vector<SkeletonIkNode> &ikNodes();
|
||||
const std::vector<SkeletonIkNode>& ikNodes();
|
||||
signals:
|
||||
void finished();
|
||||
public slots:
|
||||
void process();
|
||||
|
||||
private:
|
||||
void resolve();
|
||||
|
||||
private:
|
||||
unsigned long long m_updateVersion = 0;
|
||||
std::vector<SkeletonIkNode> m_ikNodes;
|
||||
|
|
|
@ -1,8 +1,8 @@
|
|||
#include "spinnable_toolbar_icon.h"
|
||||
#include "theme.h"
|
||||
|
||||
SpinnableToolbarIcon::SpinnableToolbarIcon(QWidget *parent) :
|
||||
QWidget(parent)
|
||||
SpinnableToolbarIcon::SpinnableToolbarIcon(QWidget* parent)
|
||||
: QWidget(parent)
|
||||
{
|
||||
setFixedSize(Theme::toolIconSize, Theme::toolIconSize);
|
||||
|
||||
|
|
|
@ -1,18 +1,18 @@
|
|||
#ifndef DUST3D_APPLICATION_SPINNABLE_TOOLBAR_ICON_H_
|
||||
#define DUST3D_APPLICATION_SPINNABLE_TOOLBAR_ICON_H_
|
||||
|
||||
#include <QWidget>
|
||||
#include "waitingspinnerwidget.h"
|
||||
#include "toolbar_button.h"
|
||||
#include "waitingspinnerwidget.h"
|
||||
#include <QWidget>
|
||||
|
||||
class SpinnableToolbarIcon : public QWidget
|
||||
{
|
||||
class SpinnableToolbarIcon : public QWidget {
|
||||
public:
|
||||
SpinnableToolbarIcon(QWidget *parent=nullptr);
|
||||
void showSpinner(bool showSpinner=true);
|
||||
SpinnableToolbarIcon(QWidget* parent = nullptr);
|
||||
void showSpinner(bool showSpinner = true);
|
||||
bool isSpinning();
|
||||
|
||||
private:
|
||||
WaitingSpinnerWidget *m_spinner = nullptr;
|
||||
WaitingSpinnerWidget* m_spinner = nullptr;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
@ -1,19 +1,19 @@
|
|||
#include <QPainter>
|
||||
#include <QGuiApplication>
|
||||
#include <QRegion>
|
||||
#include <QPolygon>
|
||||
#include <QElapsedTimer>
|
||||
#include <QRadialGradient>
|
||||
#include <dust3d/base/texture_type.h>
|
||||
#include "texture_generator.h"
|
||||
#include "theme.h"
|
||||
#include "material.h"
|
||||
#include "debug.h"
|
||||
#include "material.h"
|
||||
#include "theme.h"
|
||||
#include <QElapsedTimer>
|
||||
#include <QGuiApplication>
|
||||
#include <QPainter>
|
||||
#include <QPolygon>
|
||||
#include <QRadialGradient>
|
||||
#include <QRegion>
|
||||
#include <dust3d/base/texture_type.h>
|
||||
|
||||
QColor TextureGenerator::m_defaultTextureColor = Qt::transparent;
|
||||
|
||||
TextureGenerator::TextureGenerator(const dust3d::Object &object, dust3d::Snapshot *snapshot) :
|
||||
m_snapshot(snapshot)
|
||||
TextureGenerator::TextureGenerator(const dust3d::Object& object, dust3d::Snapshot* snapshot)
|
||||
: m_snapshot(snapshot)
|
||||
{
|
||||
m_object = new dust3d::Object();
|
||||
*m_object = object;
|
||||
|
@ -31,84 +31,84 @@ TextureGenerator::~TextureGenerator()
|
|||
delete m_snapshot;
|
||||
}
|
||||
|
||||
QImage *TextureGenerator::takeResultTextureColorImage()
|
||||
QImage* TextureGenerator::takeResultTextureColorImage()
|
||||
{
|
||||
QImage *resultTextureColorImage = m_resultTextureColorImage;
|
||||
QImage* resultTextureColorImage = m_resultTextureColorImage;
|
||||
m_resultTextureColorImage = nullptr;
|
||||
return resultTextureColorImage;
|
||||
}
|
||||
|
||||
QImage *TextureGenerator::takeResultTextureNormalImage()
|
||||
QImage* TextureGenerator::takeResultTextureNormalImage()
|
||||
{
|
||||
QImage *resultTextureNormalImage = m_resultTextureNormalImage;
|
||||
QImage* resultTextureNormalImage = m_resultTextureNormalImage;
|
||||
m_resultTextureNormalImage = nullptr;
|
||||
return resultTextureNormalImage;
|
||||
}
|
||||
|
||||
QImage *TextureGenerator::takeResultTextureRoughnessImage()
|
||||
QImage* TextureGenerator::takeResultTextureRoughnessImage()
|
||||
{
|
||||
QImage *resultTextureRoughnessImage = m_resultTextureRoughnessImage;
|
||||
QImage* resultTextureRoughnessImage = m_resultTextureRoughnessImage;
|
||||
m_resultTextureRoughnessImage = nullptr;
|
||||
return resultTextureRoughnessImage;
|
||||
}
|
||||
|
||||
QImage *TextureGenerator::takeResultTextureMetalnessImage()
|
||||
QImage* TextureGenerator::takeResultTextureMetalnessImage()
|
||||
{
|
||||
QImage *resultTextureMetalnessImage = m_resultTextureMetalnessImage;
|
||||
QImage* resultTextureMetalnessImage = m_resultTextureMetalnessImage;
|
||||
m_resultTextureMetalnessImage = nullptr;
|
||||
return resultTextureMetalnessImage;
|
||||
}
|
||||
|
||||
QImage *TextureGenerator::takeResultTextureAmbientOcclusionImage()
|
||||
QImage* TextureGenerator::takeResultTextureAmbientOcclusionImage()
|
||||
{
|
||||
QImage *resultTextureAmbientOcclusionImage = m_resultTextureAmbientOcclusionImage;
|
||||
QImage* resultTextureAmbientOcclusionImage = m_resultTextureAmbientOcclusionImage;
|
||||
m_resultTextureAmbientOcclusionImage = nullptr;
|
||||
return resultTextureAmbientOcclusionImage;
|
||||
}
|
||||
|
||||
dust3d::Object *TextureGenerator::takeObject()
|
||||
dust3d::Object* TextureGenerator::takeObject()
|
||||
{
|
||||
dust3d::Object *object = m_object;
|
||||
dust3d::Object* object = m_object;
|
||||
m_object = nullptr;
|
||||
return object;
|
||||
}
|
||||
|
||||
ModelMesh *TextureGenerator::takeResultMesh()
|
||||
ModelMesh* TextureGenerator::takeResultMesh()
|
||||
{
|
||||
ModelMesh *resultMesh = m_resultMesh;
|
||||
ModelMesh* resultMesh = m_resultMesh;
|
||||
m_resultMesh = nullptr;
|
||||
return resultMesh;
|
||||
}
|
||||
|
||||
void TextureGenerator::addPartColorMap(dust3d::Uuid partId, const QImage *image, float tileScale)
|
||||
void TextureGenerator::addPartColorMap(dust3d::Uuid partId, const QImage* image, float tileScale)
|
||||
{
|
||||
if (nullptr == image)
|
||||
return;
|
||||
m_partColorTextureMap[partId] = std::make_pair(*image, tileScale);
|
||||
}
|
||||
|
||||
void TextureGenerator::addPartNormalMap(dust3d::Uuid partId, const QImage *image, float tileScale)
|
||||
void TextureGenerator::addPartNormalMap(dust3d::Uuid partId, const QImage* image, float tileScale)
|
||||
{
|
||||
if (nullptr == image)
|
||||
return;
|
||||
m_partNormalTextureMap[partId] = std::make_pair(*image, tileScale);
|
||||
}
|
||||
|
||||
void TextureGenerator::addPartMetalnessMap(dust3d::Uuid partId, const QImage *image, float tileScale)
|
||||
void TextureGenerator::addPartMetalnessMap(dust3d::Uuid partId, const QImage* image, float tileScale)
|
||||
{
|
||||
if (nullptr == image)
|
||||
return;
|
||||
m_partMetalnessTextureMap[partId] = std::make_pair(*image, tileScale);
|
||||
}
|
||||
|
||||
void TextureGenerator::addPartRoughnessMap(dust3d::Uuid partId, const QImage *image, float tileScale)
|
||||
void TextureGenerator::addPartRoughnessMap(dust3d::Uuid partId, const QImage* image, float tileScale)
|
||||
{
|
||||
if (nullptr == image)
|
||||
return;
|
||||
m_partRoughnessTextureMap[partId] = std::make_pair(*image, tileScale);
|
||||
}
|
||||
|
||||
void TextureGenerator::addPartAmbientOcclusionMap(dust3d::Uuid partId, const QImage *image, float tileScale)
|
||||
void TextureGenerator::addPartAmbientOcclusionMap(dust3d::Uuid partId, const QImage* image, float tileScale)
|
||||
{
|
||||
if (nullptr == image)
|
||||
return;
|
||||
|
@ -122,17 +122,17 @@ void TextureGenerator::prepare()
|
|||
|
||||
std::map<dust3d::Uuid, dust3d::Uuid> updatedMaterialIdMap;
|
||||
std::map<dust3d::Uuid, bool> updatedCountershadedMap;
|
||||
for (const auto &partIt: m_snapshot->parts) {
|
||||
for (const auto& partIt : m_snapshot->parts) {
|
||||
dust3d::Uuid materialId;
|
||||
auto materialIdIt = partIt.second.find("materialId");
|
||||
if (materialIdIt != partIt.second.end())
|
||||
materialId = dust3d::Uuid(materialIdIt->second);
|
||||
dust3d::Uuid partId = dust3d::Uuid(partIt.first);
|
||||
updatedMaterialIdMap.insert({partId, materialId});
|
||||
updatedCountershadedMap.insert({partId,
|
||||
dust3d::String::isTrue(dust3d::String::valueOrEmpty(partIt.second, "countershaded"))});
|
||||
updatedMaterialIdMap.insert({ partId, materialId });
|
||||
updatedCountershadedMap.insert({ partId,
|
||||
dust3d::String::isTrue(dust3d::String::valueOrEmpty(partIt.second, "countershaded")) });
|
||||
}
|
||||
for (const auto &bmeshNode: m_object->nodes) {
|
||||
for (const auto& bmeshNode : m_object->nodes) {
|
||||
|
||||
bool countershaded = bmeshNode.countershaded;
|
||||
auto findUpdatedCountershadedMap = updatedCountershadedMap.find(bmeshNode.mirrorFromPartId.isNull() ? bmeshNode.partId : bmeshNode.mirrorFromPartId);
|
||||
|
@ -150,7 +150,7 @@ void TextureGenerator::prepare()
|
|||
materialId = findUpdatedMaterialIdResult->second;
|
||||
float tileScale = 1.0;
|
||||
initializeMaterialTexturesFromSnapshot(*m_snapshot, materialId, materialTextures, tileScale);
|
||||
const QImage *image = materialTextures.textureImages[i];
|
||||
const QImage* image = materialTextures.textureImages[i];
|
||||
if (nullptr != image) {
|
||||
if (dust3d::TextureType::BaseColor == forWhat)
|
||||
addPartColorMap(bmeshNode.partId, image, tileScale);
|
||||
|
@ -193,26 +193,26 @@ void TextureGenerator::generate()
|
|||
bool hasRoughnessMap = false;
|
||||
bool hasAmbientOcclusionMap = false;
|
||||
|
||||
const auto &triangleVertexUvs = *m_object->triangleVertexUvs();
|
||||
const auto &triangleSourceNodes = *m_object->triangleSourceNodes();
|
||||
const auto &partUvRects = *m_object->partUvRects();
|
||||
const auto &triangleNormals = m_object->triangleNormals;
|
||||
const auto& triangleVertexUvs = *m_object->triangleVertexUvs();
|
||||
const auto& triangleSourceNodes = *m_object->triangleSourceNodes();
|
||||
const auto& partUvRects = *m_object->partUvRects();
|
||||
const auto& triangleNormals = m_object->triangleNormals;
|
||||
|
||||
std::map<dust3d::Uuid, QColor> partColorMap;
|
||||
std::map<std::pair<dust3d::Uuid, dust3d::Uuid>, const dust3d::ObjectNode *> nodeMap;
|
||||
std::map<std::pair<dust3d::Uuid, dust3d::Uuid>, const dust3d::ObjectNode*> nodeMap;
|
||||
std::map<dust3d::Uuid, float> partColorSolubilityMap;
|
||||
std::map<dust3d::Uuid, float> partMetalnessMap;
|
||||
std::map<dust3d::Uuid, float> partRoughnessMap;
|
||||
for (const auto &item: m_object->nodes) {
|
||||
for (const auto& item : m_object->nodes) {
|
||||
if (!m_hasTransparencySettings) {
|
||||
if (!qFuzzyCompare(1.0, item.color.alpha()))
|
||||
m_hasTransparencySettings = true;
|
||||
}
|
||||
nodeMap.insert({{item.partId, item.nodeId}, &item});
|
||||
partColorMap.insert({item.partId, QColor(item.color.toString().c_str())});
|
||||
partColorSolubilityMap.insert({item.partId, item.colorSolubility});
|
||||
partMetalnessMap.insert({item.partId, item.metalness});
|
||||
partRoughnessMap.insert({item.partId, item.roughness});
|
||||
nodeMap.insert({ { item.partId, item.nodeId }, &item });
|
||||
partColorMap.insert({ item.partId, QColor(item.color.toString().c_str()) });
|
||||
partColorSolubilityMap.insert({ item.partId, item.colorSolubility });
|
||||
partMetalnessMap.insert({ item.partId, item.metalness });
|
||||
partRoughnessMap.insert({ item.partId, item.roughness });
|
||||
}
|
||||
|
||||
m_resultTextureColorImage = new QImage(TextureGenerator::m_textureSize, TextureGenerator::m_textureSize, QImage::Format_ARGB32);
|
||||
|
@ -260,15 +260,15 @@ void TextureGenerator::generate()
|
|||
|
||||
texturePainter.setPen(Qt::NoPen);
|
||||
|
||||
for (const auto &it: partUvRects) {
|
||||
const auto &partId = it.first;
|
||||
const auto &rects = it.second;
|
||||
for (const auto& it : partUvRects) {
|
||||
const auto& partId = it.first;
|
||||
const auto& rects = it.second;
|
||||
auto findSourceColorResult = partColorMap.find(partId);
|
||||
if (findSourceColorResult != partColorMap.end()) {
|
||||
const auto &color = findSourceColorResult->second;
|
||||
const auto& color = findSourceColorResult->second;
|
||||
QBrush brush(color);
|
||||
float fillExpandSize = 2;
|
||||
for (const auto &rect: rects) {
|
||||
for (const auto& rect : rects) {
|
||||
QRectF translatedRect = {
|
||||
rect.left() * TextureGenerator::m_textureSize - fillExpandSize,
|
||||
rect.top() * TextureGenerator::m_textureSize - fillExpandSize,
|
||||
|
@ -280,19 +280,19 @@ void TextureGenerator::generate()
|
|||
}
|
||||
}
|
||||
|
||||
for (const auto &it: partUvRects) {
|
||||
const auto &partId = it.first;
|
||||
const auto &rects = it.second;
|
||||
for (const auto& it : partUvRects) {
|
||||
const auto& partId = it.first;
|
||||
const auto& rects = it.second;
|
||||
auto findMetalnessResult = partMetalnessMap.find(partId);
|
||||
if (findMetalnessResult != partMetalnessMap.end()) {
|
||||
if (qFuzzyCompare(findMetalnessResult->second, (float)0.0))
|
||||
continue;
|
||||
const auto &color = QColor(findMetalnessResult->second * 255,
|
||||
const auto& color = QColor(findMetalnessResult->second * 255,
|
||||
findMetalnessResult->second * 255,
|
||||
findMetalnessResult->second * 255);
|
||||
QBrush brush(color);
|
||||
float fillExpandSize = 2;
|
||||
for (const auto &rect: rects) {
|
||||
for (const auto& rect : rects) {
|
||||
QRectF translatedRect = {
|
||||
rect.left() * TextureGenerator::m_textureSize - fillExpandSize,
|
||||
rect.top() * TextureGenerator::m_textureSize - fillExpandSize,
|
||||
|
@ -305,19 +305,19 @@ void TextureGenerator::generate()
|
|||
}
|
||||
}
|
||||
|
||||
for (const auto &it: partUvRects) {
|
||||
const auto &partId = it.first;
|
||||
const auto &rects = it.second;
|
||||
for (const auto& it : partUvRects) {
|
||||
const auto& partId = it.first;
|
||||
const auto& rects = it.second;
|
||||
auto findRoughnessResult = partRoughnessMap.find(partId);
|
||||
if (findRoughnessResult != partRoughnessMap.end()) {
|
||||
if (qFuzzyCompare(findRoughnessResult->second, (float)1.0))
|
||||
continue;
|
||||
const auto &color = QColor(findRoughnessResult->second * 255,
|
||||
const auto& color = QColor(findRoughnessResult->second * 255,
|
||||
findRoughnessResult->second * 255,
|
||||
findRoughnessResult->second * 255);
|
||||
QBrush brush(color);
|
||||
float fillExpandSize = 2;
|
||||
for (const auto &rect: rects) {
|
||||
for (const auto& rect : rects) {
|
||||
QRectF translatedRect = {
|
||||
rect.left() * TextureGenerator::m_textureSize - fillExpandSize,
|
||||
rect.top() * TextureGenerator::m_textureSize - fillExpandSize,
|
||||
|
@ -330,24 +330,24 @@ void TextureGenerator::generate()
|
|||
}
|
||||
}
|
||||
|
||||
auto drawTexture = [&](const std::map<dust3d::Uuid, std::pair<QPixmap, QPixmap>> &map, QPainter &painter, bool useAlpha) {
|
||||
for (const auto &it: partUvRects) {
|
||||
const auto &partId = it.first;
|
||||
const auto &rects = it.second;
|
||||
auto drawTexture = [&](const std::map<dust3d::Uuid, std::pair<QPixmap, QPixmap>>& map, QPainter& painter, bool useAlpha) {
|
||||
for (const auto& it : partUvRects) {
|
||||
const auto& partId = it.first;
|
||||
const auto& rects = it.second;
|
||||
float alpha = 1.0;
|
||||
if (useAlpha) {
|
||||
auto findSourceColorResult = partColorMap.find(partId);
|
||||
if (findSourceColorResult != partColorMap.end()) {
|
||||
const auto &color = findSourceColorResult->second;
|
||||
const auto& color = findSourceColorResult->second;
|
||||
alpha = color.alphaF();
|
||||
}
|
||||
}
|
||||
auto findTextureResult = map.find(partId);
|
||||
if (findTextureResult != map.end()) {
|
||||
const auto &pixmap = findTextureResult->second.first;
|
||||
const auto &rotatedPixmap = findTextureResult->second.second;
|
||||
const auto& pixmap = findTextureResult->second.first;
|
||||
const auto& rotatedPixmap = findTextureResult->second.second;
|
||||
painter.setOpacity(alpha);
|
||||
for (const auto &rect: rects) {
|
||||
for (const auto& rect : rects) {
|
||||
QRectF translatedRect = {
|
||||
rect.left() * TextureGenerator::m_textureSize,
|
||||
rect.top() * TextureGenerator::m_textureSize,
|
||||
|
@ -365,11 +365,11 @@ void TextureGenerator::generate()
|
|||
}
|
||||
};
|
||||
|
||||
auto convertTextureImageToPixmap = [&](const std::map<dust3d::Uuid, std::pair<QImage, float>> &sourceMap,
|
||||
std::map<dust3d::Uuid, std::pair<QPixmap, QPixmap>> &targetMap) {
|
||||
for (const auto &it: sourceMap) {
|
||||
auto convertTextureImageToPixmap = [&](const std::map<dust3d::Uuid, std::pair<QImage, float>>& sourceMap,
|
||||
std::map<dust3d::Uuid, std::pair<QPixmap, QPixmap>>& targetMap) {
|
||||
for (const auto& it : sourceMap) {
|
||||
float tileScale = it.second.second;
|
||||
const auto &image = it.second.first;
|
||||
const auto& image = it.second.first;
|
||||
auto newSize = image.size() * tileScale;
|
||||
QImage scaledImage = image.scaled(newSize);
|
||||
QPoint center = scaledImage.rect().center();
|
||||
|
@ -400,34 +400,33 @@ void TextureGenerator::generate()
|
|||
drawTexture(partRoughnessTexturePixmaps, textureRoughnessPainter, false);
|
||||
drawTexture(partAmbientOcclusionTexturePixmaps, textureAmbientOcclusionPainter, false);
|
||||
|
||||
auto drawBySolubility = [&](const dust3d::Uuid &partId, size_t triangleIndex, size_t firstVertexIndex, size_t secondVertexIndex,
|
||||
const dust3d::Uuid &neighborPartId) {
|
||||
const std::vector<dust3d::Vector2> &uv = triangleVertexUvs[triangleIndex];
|
||||
const auto &allRects = partUvRects.find(partId);
|
||||
auto drawBySolubility = [&](const dust3d::Uuid& partId, size_t triangleIndex, size_t firstVertexIndex, size_t secondVertexIndex,
|
||||
const dust3d::Uuid& neighborPartId) {
|
||||
const std::vector<dust3d::Vector2>& uv = triangleVertexUvs[triangleIndex];
|
||||
const auto& allRects = partUvRects.find(partId);
|
||||
if (allRects == partUvRects.end()) {
|
||||
qDebug() << "Found part uv rects failed";
|
||||
return;
|
||||
}
|
||||
const auto &firstPoint = uv[firstVertexIndex];
|
||||
const auto &secondPoint = uv[secondVertexIndex];
|
||||
const auto& firstPoint = uv[firstVertexIndex];
|
||||
const auto& secondPoint = uv[secondVertexIndex];
|
||||
auto edgeLength = (firstPoint - secondPoint).length();
|
||||
auto middlePoint = (firstPoint + secondPoint) / 2.0;
|
||||
float alpha = 1.0;
|
||||
const auto &findColor = partColorMap.find(partId);
|
||||
const auto& findColor = partColorMap.find(partId);
|
||||
if (findColor == partColorMap.end())
|
||||
return;
|
||||
alpha = findColor->second.alphaF();
|
||||
const auto &findNeighborColorSolubility = partColorSolubilityMap.find(neighborPartId);
|
||||
const auto& findNeighborColorSolubility = partColorSolubilityMap.find(neighborPartId);
|
||||
if (findNeighborColorSolubility == partColorSolubilityMap.end())
|
||||
return;
|
||||
if (qFuzzyIsNull(findNeighborColorSolubility->second))
|
||||
return;
|
||||
const auto &findNeighborColor = partColorMap.find(neighborPartId);
|
||||
const auto& findNeighborColor = partColorMap.find(neighborPartId);
|
||||
if (findNeighborColor == partColorMap.end())
|
||||
return;
|
||||
for (const auto &it: allRects->second) {
|
||||
if (it.contains(firstPoint.x(), firstPoint.y()) ||
|
||||
it.contains(secondPoint.x(), secondPoint.y())) {
|
||||
for (const auto& it : allRects->second) {
|
||||
if (it.contains(firstPoint.x(), firstPoint.y()) || it.contains(secondPoint.x(), secondPoint.y())) {
|
||||
float finalRadius = (it.width() + it.height()) * 0.5 * findNeighborColorSolubility->second;
|
||||
if (finalRadius < edgeLength)
|
||||
finalRadius = edgeLength;
|
||||
|
@ -445,8 +444,8 @@ void TextureGenerator::generate()
|
|||
texturePainter.setOpacity(alpha);
|
||||
auto findTextureResult = partColorTexturePixmaps.find(neighborPartId);
|
||||
if (findTextureResult != partColorTexturePixmaps.end()) {
|
||||
const auto &pixmap = findTextureResult->second.first;
|
||||
const auto &rotatedPixmap = findTextureResult->second.second;
|
||||
const auto& pixmap = findTextureResult->second.first;
|
||||
const auto& rotatedPixmap = findTextureResult->second.second;
|
||||
|
||||
QImage tmpImage(translatedRect.width(), translatedRect.height(), QImage::Format_ARGB32);
|
||||
QPixmap tmpPixmap = QPixmap::fromImage(tmpImage);
|
||||
|
@ -466,7 +465,7 @@ void TextureGenerator::generate()
|
|||
|
||||
// Apply gradient
|
||||
QRadialGradient gradient(QPointF(middlePoint.x() * TextureGenerator::m_textureSize - translatedRect.left(),
|
||||
middlePoint.y() * TextureGenerator::m_textureSize - translatedRect.top()),
|
||||
middlePoint.y() * TextureGenerator::m_textureSize - translatedRect.top()),
|
||||
finalRadius * TextureGenerator::m_textureSize);
|
||||
gradient.setColorAt(0.0, findNeighborColor->second);
|
||||
gradient.setColorAt(1.0, Qt::transparent);
|
||||
|
@ -479,7 +478,7 @@ void TextureGenerator::generate()
|
|||
texturePainter.drawPixmap(translatedRect, tmpPixmap, tmpImageFrame);
|
||||
} else {
|
||||
QRadialGradient gradient(QPointF(middlePoint.x() * TextureGenerator::m_textureSize,
|
||||
middlePoint.y() * TextureGenerator::m_textureSize),
|
||||
middlePoint.y() * TextureGenerator::m_textureSize),
|
||||
finalRadius * TextureGenerator::m_textureSize);
|
||||
gradient.setColorAt(0.0, findNeighborColor->second);
|
||||
gradient.setColorAt(1.0, Qt::transparent);
|
||||
|
@ -493,7 +492,7 @@ void TextureGenerator::generate()
|
|||
|
||||
std::map<std::pair<size_t, size_t>, std::tuple<size_t, size_t, size_t>> halfEdgeToTriangleMap;
|
||||
for (size_t i = 0; i < m_object->triangles.size(); ++i) {
|
||||
const auto &triangleIndices = m_object->triangles[i];
|
||||
const auto& triangleIndices = m_object->triangles[i];
|
||||
if (triangleIndices.size() != 3) {
|
||||
qDebug() << "Found invalid triangle indices";
|
||||
continue;
|
||||
|
@ -504,13 +503,13 @@ void TextureGenerator::generate()
|
|||
std::make_tuple(i, j, k)));
|
||||
}
|
||||
}
|
||||
for (const auto &it: halfEdgeToTriangleMap) {
|
||||
for (const auto& it : halfEdgeToTriangleMap) {
|
||||
auto oppositeHalfEdge = std::make_pair(it.first.second, it.first.first);
|
||||
const auto &opposite = halfEdgeToTriangleMap.find(oppositeHalfEdge);
|
||||
const auto& opposite = halfEdgeToTriangleMap.find(oppositeHalfEdge);
|
||||
if (opposite == halfEdgeToTriangleMap.end())
|
||||
continue;
|
||||
const std::pair<dust3d::Uuid, dust3d::Uuid> &source = triangleSourceNodes[std::get<0>(it.second)];
|
||||
const std::pair<dust3d::Uuid, dust3d::Uuid> &oppositeSource = triangleSourceNodes[std::get<0>(opposite->second)];
|
||||
const std::pair<dust3d::Uuid, dust3d::Uuid>& source = triangleSourceNodes[std::get<0>(it.second)];
|
||||
const std::pair<dust3d::Uuid, dust3d::Uuid>& oppositeSource = triangleSourceNodes[std::get<0>(opposite->second)];
|
||||
if (source.first == oppositeSource.first)
|
||||
continue;
|
||||
drawBySolubility(source.first, std::get<0>(it.second), std::get<1>(it.second), std::get<2>(it.second), oppositeSource.first);
|
||||
|
@ -520,22 +519,22 @@ void TextureGenerator::generate()
|
|||
// Draw belly white
|
||||
texturePainter.setCompositionMode(QPainter::CompositionMode_SoftLight);
|
||||
for (size_t triangleIndex = 0; triangleIndex < m_object->triangles.size(); ++triangleIndex) {
|
||||
const auto &normal = triangleNormals[triangleIndex];
|
||||
const std::pair<dust3d::Uuid, dust3d::Uuid> &source = triangleSourceNodes[triangleIndex];
|
||||
const auto &partId = source.first;
|
||||
const auto& normal = triangleNormals[triangleIndex];
|
||||
const std::pair<dust3d::Uuid, dust3d::Uuid>& source = triangleSourceNodes[triangleIndex];
|
||||
const auto& partId = source.first;
|
||||
if (m_countershadedPartIds.find(partId) == m_countershadedPartIds.end())
|
||||
continue;
|
||||
|
||||
const auto &allRects = partUvRects.find(partId);
|
||||
const auto& allRects = partUvRects.find(partId);
|
||||
if (allRects == partUvRects.end()) {
|
||||
qDebug() << "Found part uv rects failed";
|
||||
continue;
|
||||
}
|
||||
|
||||
const auto &findObjectNode = nodeMap.find(source);
|
||||
const auto& findObjectNode = nodeMap.find(source);
|
||||
if (findObjectNode == nodeMap.end())
|
||||
continue;
|
||||
const dust3d::ObjectNode *objectNode = findObjectNode->second;
|
||||
const dust3d::ObjectNode* objectNode = findObjectNode->second;
|
||||
if (qAbs(dust3d::Vector3::dotProduct(objectNode->direction, dust3d::Vector3(0, 1, 0))) >= 0.707) {
|
||||
if (dust3d::Vector3::dotProduct(normal, dust3d::Vector3(0, 0, 1)) <= 0.0)
|
||||
continue;
|
||||
|
@ -544,23 +543,21 @@ void TextureGenerator::generate()
|
|||
continue;
|
||||
}
|
||||
|
||||
const auto &triangleIndices = m_object->triangles[triangleIndex];
|
||||
const auto& triangleIndices = m_object->triangles[triangleIndex];
|
||||
if (triangleIndices.size() != 3) {
|
||||
qDebug() << "Found invalid triangle indices";
|
||||
continue;
|
||||
}
|
||||
|
||||
const std::vector<dust3d::Vector2> &uv = triangleVertexUvs[triangleIndex];
|
||||
const std::vector<dust3d::Vector2>& uv = triangleVertexUvs[triangleIndex];
|
||||
dust3d::Vector2 middlePoint = (uv[0] + uv[1] + uv[2]) / 3.0;
|
||||
float finalRadius = ((uv[0] - uv[1]).length() +
|
||||
(uv[1] - uv[2]).length() +
|
||||
(uv[2] - uv[0]).length()) / 3.0;
|
||||
float finalRadius = ((uv[0] - uv[1]).length() + (uv[1] - uv[2]).length() + (uv[2] - uv[0]).length()) / 3.0;
|
||||
QRadialGradient gradient(QPointF(middlePoint.x() * TextureGenerator::m_textureSize,
|
||||
middlePoint.y() * TextureGenerator::m_textureSize),
|
||||
middlePoint.y() * TextureGenerator::m_textureSize),
|
||||
finalRadius * TextureGenerator::m_textureSize);
|
||||
gradient.setColorAt(0.0, Qt::white);
|
||||
gradient.setColorAt(1.0, Qt::transparent);
|
||||
for (const auto &it: allRects->second) {
|
||||
for (const auto& it : allRects->second) {
|
||||
if (it.contains(middlePoint.x(), middlePoint.y())) {
|
||||
dust3d::Rectangle fillTarget((middlePoint.x() - finalRadius),
|
||||
(middlePoint.y() - finalRadius),
|
||||
|
@ -581,26 +578,26 @@ void TextureGenerator::generate()
|
|||
for (int i = 0; i < 3; ++i) {
|
||||
int j = (i + 1) % 3;
|
||||
auto oppositeHalfEdge = std::make_pair(triangleIndices[j], triangleIndices[i]);
|
||||
const auto &opposite = halfEdgeToTriangleMap.find(oppositeHalfEdge);
|
||||
const auto& opposite = halfEdgeToTriangleMap.find(oppositeHalfEdge);
|
||||
if (opposite == halfEdgeToTriangleMap.end())
|
||||
continue;
|
||||
auto oppositeTriangleIndex = std::get<0>(opposite->second);
|
||||
const std::pair<dust3d::Uuid, dust3d::Uuid> &oppositeSource = triangleSourceNodes[oppositeTriangleIndex];
|
||||
const std::pair<dust3d::Uuid, dust3d::Uuid>& oppositeSource = triangleSourceNodes[oppositeTriangleIndex];
|
||||
if (partId == oppositeSource.first)
|
||||
continue;
|
||||
const auto &oppositeAllRects = partUvRects.find(oppositeSource.first);
|
||||
const auto& oppositeAllRects = partUvRects.find(oppositeSource.first);
|
||||
if (oppositeAllRects == partUvRects.end()) {
|
||||
qDebug() << "Found part uv rects failed";
|
||||
continue;
|
||||
}
|
||||
const std::vector<dust3d::Vector2> &oppositeUv = triangleVertexUvs[oppositeTriangleIndex];
|
||||
const std::vector<dust3d::Vector2>& oppositeUv = triangleVertexUvs[oppositeTriangleIndex];
|
||||
dust3d::Vector2 oppositeMiddlePoint = (oppositeUv[std::get<1>(opposite->second)] + oppositeUv[std::get<2>(opposite->second)]) * 0.5;
|
||||
QRadialGradient oppositeGradient(QPointF(oppositeMiddlePoint.x() * TextureGenerator::m_textureSize,
|
||||
oppositeMiddlePoint.y() * TextureGenerator::m_textureSize),
|
||||
oppositeMiddlePoint.y() * TextureGenerator::m_textureSize),
|
||||
finalRadius * TextureGenerator::m_textureSize);
|
||||
oppositeGradient.setColorAt(0.0, Qt::white);
|
||||
oppositeGradient.setColorAt(1.0, Qt::transparent);
|
||||
for (const auto &it: oppositeAllRects->second) {
|
||||
for (const auto& it : oppositeAllRects->second) {
|
||||
if (it.contains(oppositeMiddlePoint.x(), oppositeMiddlePoint.y())) {
|
||||
dust3d::Rectangle fillTarget((oppositeMiddlePoint.x() - finalRadius),
|
||||
(oppositeMiddlePoint.y() - finalRadius),
|
||||
|
@ -664,14 +661,12 @@ void TextureGenerator::generate()
|
|||
qDebug() << "The texture[" << TextureGenerator::m_textureSize << "x" << TextureGenerator::m_textureSize << "] generation took" << countTimeConsumed.elapsed() << "milliseconds";
|
||||
}
|
||||
|
||||
QImage *TextureGenerator::combineMetalnessRoughnessAmbientOcclusionImages(QImage *metalnessImage,
|
||||
QImage *roughnessImage,
|
||||
QImage *ambientOcclusionImage)
|
||||
QImage* TextureGenerator::combineMetalnessRoughnessAmbientOcclusionImages(QImage* metalnessImage,
|
||||
QImage* roughnessImage,
|
||||
QImage* ambientOcclusionImage)
|
||||
{
|
||||
QImage *textureMetalnessRoughnessAmbientOcclusionImage = nullptr;
|
||||
if (nullptr != metalnessImage ||
|
||||
nullptr != roughnessImage ||
|
||||
nullptr != ambientOcclusionImage) {
|
||||
QImage* textureMetalnessRoughnessAmbientOcclusionImage = nullptr;
|
||||
if (nullptr != metalnessImage || nullptr != roughnessImage || nullptr != ambientOcclusionImage) {
|
||||
int textureSize = 0;
|
||||
if (nullptr != metalnessImage)
|
||||
textureSize = metalnessImage->height();
|
||||
|
|
|
@ -1,61 +1,63 @@
|
|||
#ifndef DUST3D_APPLICATION_TEXTURE_GENERATOR_H_
|
||||
#define DUST3D_APPLICATION_TEXTURE_GENERATOR_H_
|
||||
|
||||
#include <QObject>
|
||||
#include <vector>
|
||||
#include <QImage>
|
||||
#include "model_mesh.h"
|
||||
#include <QColor>
|
||||
#include <QImage>
|
||||
#include <QObject>
|
||||
#include <QPixmap>
|
||||
#include <dust3d/base/object.h>
|
||||
#include <dust3d/base/snapshot.h>
|
||||
#include "model_mesh.h"
|
||||
#include <vector>
|
||||
|
||||
class TextureGenerator : public QObject
|
||||
{
|
||||
class TextureGenerator : public QObject {
|
||||
Q_OBJECT
|
||||
public:
|
||||
TextureGenerator(const dust3d::Object &object, dust3d::Snapshot *snapshot=nullptr);
|
||||
TextureGenerator(const dust3d::Object& object, dust3d::Snapshot* snapshot = nullptr);
|
||||
~TextureGenerator();
|
||||
QImage *takeResultTextureColorImage();
|
||||
QImage *takeResultTextureNormalImage();
|
||||
QImage *takeResultTextureRoughnessImage();
|
||||
QImage *takeResultTextureMetalnessImage();
|
||||
QImage *takeResultTextureAmbientOcclusionImage();
|
||||
dust3d::Object *takeObject();
|
||||
ModelMesh *takeResultMesh();
|
||||
QImage* takeResultTextureColorImage();
|
||||
QImage* takeResultTextureNormalImage();
|
||||
QImage* takeResultTextureRoughnessImage();
|
||||
QImage* takeResultTextureMetalnessImage();
|
||||
QImage* takeResultTextureAmbientOcclusionImage();
|
||||
dust3d::Object* takeObject();
|
||||
ModelMesh* takeResultMesh();
|
||||
bool hasTransparencySettings();
|
||||
void addPartColorMap(dust3d::Uuid partId, const QImage *image, float tileScale);
|
||||
void addPartNormalMap(dust3d::Uuid partId, const QImage *image, float tileScale);
|
||||
void addPartMetalnessMap(dust3d::Uuid partId, const QImage *image, float tileScale);
|
||||
void addPartRoughnessMap(dust3d::Uuid partId, const QImage *image, float tileScale);
|
||||
void addPartAmbientOcclusionMap(dust3d::Uuid partId, const QImage *image, float tileScale);
|
||||
void addPartColorMap(dust3d::Uuid partId, const QImage* image, float tileScale);
|
||||
void addPartNormalMap(dust3d::Uuid partId, const QImage* image, float tileScale);
|
||||
void addPartMetalnessMap(dust3d::Uuid partId, const QImage* image, float tileScale);
|
||||
void addPartRoughnessMap(dust3d::Uuid partId, const QImage* image, float tileScale);
|
||||
void addPartAmbientOcclusionMap(dust3d::Uuid partId, const QImage* image, float tileScale);
|
||||
void generate();
|
||||
static QImage *combineMetalnessRoughnessAmbientOcclusionImages(QImage *metalnessImage,
|
||||
QImage *roughnessImage,
|
||||
QImage *ambientOcclusionImage);
|
||||
static QImage* combineMetalnessRoughnessAmbientOcclusionImages(QImage* metalnessImage,
|
||||
QImage* roughnessImage,
|
||||
QImage* ambientOcclusionImage);
|
||||
signals:
|
||||
void finished();
|
||||
public slots:
|
||||
void process();
|
||||
|
||||
public:
|
||||
static QColor m_defaultTextureColor;
|
||||
|
||||
private:
|
||||
void prepare();
|
||||
|
||||
private:
|
||||
dust3d::Object *m_object = nullptr;
|
||||
QImage *m_resultTextureColorImage = nullptr;
|
||||
QImage *m_resultTextureNormalImage = nullptr;
|
||||
QImage *m_resultTextureRoughnessImage = nullptr;
|
||||
QImage *m_resultTextureMetalnessImage = nullptr;
|
||||
QImage *m_resultTextureAmbientOcclusionImage = nullptr;
|
||||
ModelMesh *m_resultMesh = nullptr;
|
||||
dust3d::Object* m_object = nullptr;
|
||||
QImage* m_resultTextureColorImage = nullptr;
|
||||
QImage* m_resultTextureNormalImage = nullptr;
|
||||
QImage* m_resultTextureRoughnessImage = nullptr;
|
||||
QImage* m_resultTextureMetalnessImage = nullptr;
|
||||
QImage* m_resultTextureAmbientOcclusionImage = nullptr;
|
||||
ModelMesh* m_resultMesh = nullptr;
|
||||
std::map<dust3d::Uuid, std::pair<QImage, float>> m_partColorTextureMap;
|
||||
std::map<dust3d::Uuid, std::pair<QImage, float>> m_partNormalTextureMap;
|
||||
std::map<dust3d::Uuid, std::pair<QImage, float>> m_partMetalnessTextureMap;
|
||||
std::map<dust3d::Uuid, std::pair<QImage, float>> m_partRoughnessTextureMap;
|
||||
std::map<dust3d::Uuid, std::pair<QImage, float>> m_partAmbientOcclusionTextureMap;
|
||||
std::set<dust3d::Uuid> m_countershadedPartIds;
|
||||
dust3d::Snapshot *m_snapshot = nullptr;
|
||||
dust3d::Snapshot* m_snapshot = nullptr;
|
||||
bool m_hasTransparencySettings = false;
|
||||
int m_textureSize = 1024;
|
||||
};
|
||||
|
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue