[editor] style接入新的UI实现 | #10
parent
3edca0287b
commit
2e7d20d0d7
|
@ -104,6 +104,7 @@
|
|||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="src\Editor\EditorWidgetComponent\LayerContainerListWidget.cpp" />
|
||||
<ClCompile Include="src\Editor\DataManager\ProjectDataManager.cpp" />
|
||||
<ClCompile Include="src\Editor\EditorWidgetComponent\FillStyleWidget.cpp" />
|
||||
<ClCompile Include="src\Editor\RightBar\EditorSettingWidget.cpp" />
|
||||
|
@ -205,6 +206,7 @@
|
|||
<QtMoc Include="src\Editor\EditorWidgetComponent\ColorPicker.h" />
|
||||
<QtMoc Include="src\Editor\RightBar\EditorSettingWidget.h" />
|
||||
<QtMoc Include="src\Editor\EditorWidgetComponent\FillStyleWidget.h" />
|
||||
<QtMoc Include="src\Editor\EditorWidgetComponent\LayerContainerListWidget.h" />
|
||||
<ClInclude Include="src\Editor\DataManager\ProjectDataManager.h" />
|
||||
<ClInclude Include="src\ColorHelper.hpp" />
|
||||
<ClInclude Include="src\Editor\LayerWrapper.h" />
|
||||
|
|
|
@ -267,6 +267,9 @@
|
|||
<ClCompile Include="src\FluentMenuButton.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="src\Editor\EditorWidgetComponent\LayerContainerListWidget.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<QtMoc Include="src\Renderer\RendererGLWidget.h">
|
||||
|
@ -323,6 +326,9 @@
|
|||
<QtMoc Include="src\Editor\EditorWidgetComponent\FillStyleWidget.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</QtMoc>
|
||||
<QtMoc Include="src\Editor\EditorWidgetComponent\LayerContainerListWidget.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</QtMoc>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="..\data.json" />
|
||||
|
|
|
@ -71,7 +71,7 @@
|
|||
</widget>
|
||||
</item>
|
||||
<item row="5" column="0" colspan="2">
|
||||
<widget class="QListWidget" name="styleList"/>
|
||||
<widget class="LayerContainerListWidget" name="styleList"/>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
|
@ -86,6 +86,11 @@
|
|||
<extends>QCheckBox</extends>
|
||||
<header location="global">qtmaterialcheckbox.h</header>
|
||||
</customwidget>
|
||||
<customwidget>
|
||||
<class>LayerContainerListWidget</class>
|
||||
<extends>QListWidget</extends>
|
||||
<header location="global">EditorWidgetComponent/LayerContainerListWidget.h</header>
|
||||
</customwidget>
|
||||
</customwidgets>
|
||||
<resources/>
|
||||
<connections/>
|
||||
|
|
|
@ -41,7 +41,7 @@
|
|||
<number>0</number>
|
||||
</property>
|
||||
<item>
|
||||
<layout class="QHBoxLayout" name="horizontalLayout_2" stretch="1,1,1,1,1,0">
|
||||
<layout class="QHBoxLayout" name="horizontalLayout_2" stretch="1,1,0">
|
||||
<property name="spacing">
|
||||
<number>0</number>
|
||||
</property>
|
||||
|
@ -49,7 +49,7 @@
|
|||
<number>0</number>
|
||||
</property>
|
||||
<item>
|
||||
<widget class="QPushButton" name="createButton">
|
||||
<widget class="FluentMenuButton" name="fileMenuButton">
|
||||
<property name="minimumSize">
|
||||
<size>
|
||||
<width>80</width>
|
||||
|
@ -63,12 +63,12 @@
|
|||
</size>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>新建</string>
|
||||
<string>文件</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QPushButton" name="openButton">
|
||||
<widget class="FluentMenuButton" name="projectMenuButton">
|
||||
<property name="minimumSize">
|
||||
<size>
|
||||
<width>80</width>
|
||||
|
@ -82,70 +82,7 @@
|
|||
</size>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>打开</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QPushButton" name="saveButton">
|
||||
<property name="minimumSize">
|
||||
<size>
|
||||
<width>80</width>
|
||||
<height>40</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="maximumSize">
|
||||
<size>
|
||||
<width>80</width>
|
||||
<height>16777215</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>保存</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QPushButton" name="saveAsButton">
|
||||
<property name="minimumSize">
|
||||
<size>
|
||||
<width>80</width>
|
||||
<height>40</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="maximumSize">
|
||||
<size>
|
||||
<width>80</width>
|
||||
<height>16777215</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>另存为</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QPushButton" name="closeButton">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Fixed" vsizetype="Fixed">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="minimumSize">
|
||||
<size>
|
||||
<width>80</width>
|
||||
<height>40</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="maximumSize">
|
||||
<size>
|
||||
<width>80</width>
|
||||
<height>16777215</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>关闭</string>
|
||||
<string>项目</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
|
@ -178,6 +115,9 @@
|
|||
<property name="currentIndex">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="tabsClosable">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
<widget class="QWidget" name="tab">
|
||||
<attribute name="title">
|
||||
<string>Tab 1</string>
|
||||
|
@ -194,6 +134,13 @@
|
|||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
<customwidgets>
|
||||
<customwidget>
|
||||
<class>FluentMenuButton</class>
|
||||
<extends>QPushButton</extends>
|
||||
<header location="global">../FluentMenuButton.h</header>
|
||||
</customwidget>
|
||||
</customwidgets>
|
||||
<resources/>
|
||||
<connections/>
|
||||
</ui>
|
||||
|
|
|
@ -39,7 +39,7 @@
|
|||
<widget class="QWidget" name="MainWindow" native="true">
|
||||
<layout class="QVBoxLayout" name="verticalLayout_2" stretch="20,1">
|
||||
<item>
|
||||
<layout class="QHBoxLayout" name="horizontalLayout" stretch="0,12,5">
|
||||
<layout class="QHBoxLayout" name="horizontalLayout" stretch="0,7,4,3">
|
||||
<item>
|
||||
<widget class="QWidget" name="LeftBar" native="true"/>
|
||||
</item>
|
||||
|
@ -147,18 +147,13 @@
|
|||
</size>
|
||||
</property>
|
||||
<property name="currentIndex">
|
||||
<number>2</number>
|
||||
<number>0</number>
|
||||
</property>
|
||||
<widget class="InfoDisplayWidget" name="LayerDisplay">
|
||||
<attribute name="title">
|
||||
<string>图层信息</string>
|
||||
</attribute>
|
||||
</widget>
|
||||
<widget class="ElementPoolWidget" name="ElementDisplay">
|
||||
<attribute name="title">
|
||||
<string>图元池</string>
|
||||
</attribute>
|
||||
</widget>
|
||||
<widget class="EditorSettingWidget" name="EditorSetting">
|
||||
<attribute name="title">
|
||||
<string>设置</string>
|
||||
|
@ -201,6 +196,23 @@
|
|||
</layout>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<layout class="QVBoxLayout" name="ElementBar">
|
||||
<item>
|
||||
<widget class="QLabel" name="ElementDisplayLabel">
|
||||
<property name="text">
|
||||
<string>图元</string>
|
||||
</property>
|
||||
<property name="alignment">
|
||||
<set>Qt::AlignCenter</set>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="ElementPoolWidget" name="ElementDisplay" native="true"/>
|
||||
</item>
|
||||
</layout>
|
||||
</item>
|
||||
</layout>
|
||||
</item>
|
||||
<item>
|
||||
|
|
|
@ -8,42 +8,25 @@
|
|||
EditorWidget::EditorWidget(QWidget* parent) : QWidget(parent)
|
||||
{
|
||||
ui.setupUi(this);
|
||||
this->createButton = ui.createButton;
|
||||
this->closeButton = ui.closeButton;
|
||||
this->saveButton = ui.saveButton;
|
||||
this->saveAsButton = ui.saveAsButton;
|
||||
this->openButton = ui.openButton;
|
||||
this->fileMenuButton = ui.fileMenuButton;
|
||||
this->projectMenuButton = ui.projectMenuButton;
|
||||
this->tabWidget = ui.tabWidget;
|
||||
while (this->tabWidget->count() > 0)
|
||||
{
|
||||
this->tabWidget->removeTab(0);
|
||||
}
|
||||
connect(this->createButton, &QPushButton::clicked, this, [this]() {
|
||||
static int count = 0;
|
||||
this->tabWidget->addTab(new EditorWidgetItem("../data.json",this), "untitled" + QString::number(count++));
|
||||
});
|
||||
connect(this->openButton, &QPushButton::clicked, this, [this]() {
|
||||
QString fileName = QFileDialog::getOpenFileName(this->saveAsButton, QString::fromLocal8Bit("´ò¿ª"), "", QString::fromLocal8Bit("JSONÎļþ(*.json)"));
|
||||
if(!fileName.isEmpty())
|
||||
this->tabWidget->addTab(new EditorWidgetItem(fileName, this), fileName);
|
||||
});
|
||||
connect(this->closeButton, &QPushButton::clicked, this, [this]() {
|
||||
this->tabWidget->removeTab(this->tabWidget->currentIndex());
|
||||
});
|
||||
connect(this->saveButton, &QPushButton::clicked, this, [this]() {
|
||||
EditorWidgetItem* item = dynamic_cast<EditorWidgetItem*>(this->tabWidget->currentWidget());
|
||||
if (item != nullptr)
|
||||
{
|
||||
//item->save();
|
||||
}
|
||||
});
|
||||
connect(this->saveAsButton, &QPushButton::clicked, this, [this]() {
|
||||
EditorWidgetItem* item = dynamic_cast<EditorWidgetItem*>(this->tabWidget->currentWidget());
|
||||
if (item != nullptr)
|
||||
{
|
||||
QString fileName = QFileDialog::getSaveFileName(this->saveAsButton, QString::fromLocal8Bit("Áí´æΪ"), "", QString::fromLocal8Bit("JSONÎļþ(*.json)"));
|
||||
item->saveAs(fileName);
|
||||
}
|
||||
|
||||
connect(this, &EditorWidget::tabCountChanged, this, &EditorWidget::onTabCountChanged);
|
||||
|
||||
initFileMenu();
|
||||
initProjectMenu();
|
||||
|
||||
connect(this->tabWidget, &QTabWidget::tabCloseRequested, [this](int index) {
|
||||
const int prevCount = this->tabWidget->count();
|
||||
this->tabWidget->removeTab(index);
|
||||
const int nowCount = this->tabWidget->count();
|
||||
|
||||
emit tabCountChanged(prevCount, nowCount);
|
||||
});
|
||||
}
|
||||
|
||||
|
@ -55,3 +38,72 @@ void EditorWidget::renameTab(QWidget* target, QString name)
|
|||
this->tabWidget->setTabText(index, name);
|
||||
}
|
||||
}
|
||||
|
||||
void EditorWidget::onTabCountChanged(int prev, int now)
|
||||
{
|
||||
if (now != 0)
|
||||
{
|
||||
this->projectMenuButton->setDisabled(false);
|
||||
}
|
||||
else
|
||||
{
|
||||
this->projectMenuButton->setDisabled(true);
|
||||
}
|
||||
}
|
||||
|
||||
void EditorWidget::initFileMenu()
|
||||
{
|
||||
auto* actionCreate = new QAction(QStringLiteral("新建"), fileMenuButton);
|
||||
auto* actionOpen = new QAction(QStringLiteral("打开"), fileMenuButton);
|
||||
auto* actionSave = new QAction(QStringLiteral("保存"), fileMenuButton);
|
||||
auto* actionSaveAs = new QAction(QStringLiteral("另存为"), fileMenuButton);
|
||||
fileMenuButton->addMenuAction(actionCreate);
|
||||
fileMenuButton->addMenuAction(actionOpen);
|
||||
fileMenuButton->addMenuAction(actionSave);
|
||||
fileMenuButton->addMenuAction(actionSaveAs);
|
||||
connect(actionCreate, &QAction::triggered, [this] {
|
||||
static int count = 0;
|
||||
const int prevCount = this->tabWidget->count();
|
||||
this->tabWidget->addTab(new EditorWidgetItem("../data.json", this), "untitled" + QString::number(count++));
|
||||
const int nowCount = this->tabWidget->count();
|
||||
|
||||
emit tabCountChanged(prevCount, nowCount);
|
||||
});
|
||||
connect(actionOpen, &QAction::triggered, this, [this] {
|
||||
const QString fileName = QFileDialog::getOpenFileName(this, QStringLiteral("打开"), "", QStringLiteral("JSON文件(*.json)"));
|
||||
if (!fileName.isEmpty())
|
||||
{
|
||||
const int prevCount = this->tabWidget->count();
|
||||
this->tabWidget->addTab(new EditorWidgetItem(fileName, this), fileName);
|
||||
const int nowCount = this->tabWidget->count();
|
||||
|
||||
emit tabCountChanged(prevCount, nowCount);
|
||||
}
|
||||
});
|
||||
connect(actionSave, &QAction::triggered, this, [this] {
|
||||
auto* item = dynamic_cast<EditorWidgetItem*>(this->tabWidget->currentWidget());
|
||||
if (item != nullptr)
|
||||
{
|
||||
//item->save();
|
||||
}
|
||||
});
|
||||
connect(actionSaveAs, &QAction::triggered, this, [this] {
|
||||
const auto* item = dynamic_cast<EditorWidgetItem*>(this->tabWidget->currentWidget());
|
||||
if (item != nullptr)
|
||||
{
|
||||
const QString fileName = QFileDialog::getSaveFileName(this, QStringLiteral("另存为"), "", QStringLiteral("JSON文件(*.json)"));
|
||||
item->saveAs(fileName);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
void EditorWidget::initProjectMenu()
|
||||
{
|
||||
if (tabWidget->count() == 0)
|
||||
{
|
||||
projectMenuButton->setDisabled(true);
|
||||
}
|
||||
|
||||
auto* actionSettings = new QAction(QStringLiteral("项目设置"), projectMenuButton);
|
||||
projectMenuButton->addMenuAction(actionSettings);
|
||||
}
|
||||
|
|
|
@ -1,5 +1,6 @@
|
|||
#pragma once
|
||||
#include <qwidget.h>
|
||||
#include "../FluentMenuButton.h"
|
||||
#include "ui_EditorWidget.h"
|
||||
|
||||
class EditorWidget :
|
||||
|
@ -9,15 +10,21 @@ class EditorWidget :
|
|||
private:
|
||||
Ui::EditorWidget ui;
|
||||
QTabWidget* tabWidget;
|
||||
QPushButton* createButton;
|
||||
QPushButton* closeButton;
|
||||
QPushButton* saveButton;
|
||||
QPushButton* saveAsButton;
|
||||
QPushButton* openButton;
|
||||
FluentMenuButton* fileMenuButton;
|
||||
FluentMenuButton* projectMenuButton;
|
||||
|
||||
void initFileMenu();
|
||||
void initProjectMenu();
|
||||
|
||||
public:
|
||||
EditorWidget(QWidget* parent = nullptr);
|
||||
~EditorWidget()=default;
|
||||
void renameTab(QWidget* target, QString name);
|
||||
|
||||
protected slots:
|
||||
void onTabCountChanged(int prev, int now);
|
||||
|
||||
signals:
|
||||
void tabCountChanged(int prev, int now);
|
||||
};
|
||||
|
||||
|
|
|
@ -0,0 +1,178 @@
|
|||
#include "LayerContainerListWidget.h"
|
||||
#include "LayerStyleDialog.h"
|
||||
#include <QLabel>
|
||||
#include <ranges>
|
||||
|
||||
LayerContainerListWidget::LayerContainerListWidget(QWidget* parent, const PLayerStyleContainer& styleContainer)
|
||||
: QListWidget(parent), styleContainer(styleContainer)
|
||||
{
|
||||
connect(this, &LayerContainerListWidget::addLayerStyle,
|
||||
this, &LayerContainerListWidget::onAddLayerStyle);
|
||||
connect(this, &LayerContainerListWidget::removeLayerStyle,
|
||||
this, &LayerContainerListWidget::onRemoveLayerStyle);
|
||||
|
||||
initHeader();
|
||||
setStyleContainer(styleContainer, true);
|
||||
}
|
||||
|
||||
bool comparePStyleContainersEquality(const LayerStyleContainer* a, const LayerStyleContainer* b)
|
||||
{
|
||||
if (a == nullptr && b == nullptr)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
if (a == nullptr || b == nullptr)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
return a == b || *a == *b;
|
||||
}
|
||||
|
||||
void LayerContainerListWidget::setStyleContainer(const PLayerStyleContainer& styleContainer, bool forceRefresh)
|
||||
{
|
||||
if (!forceRefresh && comparePStyleContainersEquality(this->styleContainer, styleContainer))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
const int count = this->count();
|
||||
for (int i = 1; i < count; i++)
|
||||
{
|
||||
const auto* item = this->takeItem(1);
|
||||
delete item;
|
||||
}
|
||||
|
||||
if (!styleContainer)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
this->styleContainer = styleContainer;
|
||||
|
||||
for (auto& style : *styleContainer | std::views::values)
|
||||
{
|
||||
auto* item = new QListWidgetItem(this);
|
||||
item->setSizeHint(QSize(50, 40));
|
||||
this->setItemWidget(item, buildStyleListWidget(style));
|
||||
}
|
||||
resetAddButton();
|
||||
}
|
||||
|
||||
LayerContainerListWidget::PLayerStyleContainer LayerContainerListWidget::getStyleContainer() const
|
||||
{
|
||||
return styleContainer;
|
||||
}
|
||||
|
||||
void LayerContainerListWidget::resetAddButton()
|
||||
{
|
||||
if (!styleContainer)
|
||||
{
|
||||
return;
|
||||
}
|
||||
qDebug() << "resetAddButton" << styleContainer->full();
|
||||
addButton->setDisabled(styleContainer->full());
|
||||
}
|
||||
|
||||
void LayerContainerListWidget::onAddLayerStyle(const std::shared_ptr<LayerStyle>& style)
|
||||
{
|
||||
if (const bool ok = styleContainer->useStyle(style))
|
||||
{
|
||||
styleContainer->computeNewHash();
|
||||
resetAddButton();
|
||||
auto* newItem = new QListWidgetItem(this);
|
||||
styleItemMap[style->getDisplayName()] = newItem;
|
||||
newItem->setSizeHint(QSize(50, 40));
|
||||
this->setItemWidget(newItem, buildStyleListWidget(style));
|
||||
}
|
||||
}
|
||||
|
||||
void LayerContainerListWidget::onRemoveLayerStyle(const QString& styleName)
|
||||
{
|
||||
if (const bool ok = styleContainer->dropStyle(styleName))
|
||||
{
|
||||
styleContainer->computeNewHash();
|
||||
auto* removedItem = styleItemMap.extract(styleName).mapped();
|
||||
resetAddButton();
|
||||
delete this->takeItem(this->row(removedItem));
|
||||
}
|
||||
}
|
||||
|
||||
void LayerContainerListWidget::initHeader()
|
||||
{
|
||||
this->headerWidget = new QWidget(this);
|
||||
auto* headerLayout = new QHBoxLayout;
|
||||
|
||||
auto* headerLabel = new QLabel(headerWidget);
|
||||
headerLabel->setText(QStringLiteral("ÑùʽÁбí"));
|
||||
headerLabel->setSizePolicy(QSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding));
|
||||
|
||||
//auto* addStyleButton = new QtMaterialRaisedButton("+", headerWidget);
|
||||
this->addButton = new QPushButton("+", headerWidget);
|
||||
addButton->setFixedSize(QSize(20, 20));
|
||||
connect(addButton, &QPushButton::clicked, [this] {
|
||||
auto* dialog = new LayerStyleDialog(this->styleContainer, nullptr, this);
|
||||
dialog->exec();
|
||||
if (dialog->layerStyle)
|
||||
{
|
||||
emit addLayerStyle(dialog->layerStyle);
|
||||
}
|
||||
});
|
||||
|
||||
headerLayout->addWidget(headerLabel);
|
||||
headerLayout->addWidget(addButton);
|
||||
headerLayout->setContentsMargins(5, 0, 5, 0);
|
||||
headerWidget->setLayout(headerLayout);
|
||||
|
||||
auto* headerItem = new QListWidgetItem(this);
|
||||
headerItem->setFlags(Qt::NoItemFlags);
|
||||
this->addItem(headerItem);
|
||||
this->setItemWidget(headerItem, headerWidget);
|
||||
}
|
||||
|
||||
|
||||
QWidget* LayerContainerListWidget::buildStyleListWidget(std::shared_ptr<LayerStyle> style)
|
||||
{
|
||||
auto* w = new QWidget(this);
|
||||
auto* layout = new QHBoxLayout;
|
||||
layout->setAlignment(Qt::AlignmentFlag::AlignRight);
|
||||
//QtMaterialFlatButton* detailButton = new QtMaterialFlatButton(w);
|
||||
//QtMaterialFlatButton* removeButton = new QtMaterialFlatButton(w);
|
||||
auto* detailButton = new QPushButton(w);
|
||||
auto* removeButton = new QPushButton(w);
|
||||
detailButton->setText("...");
|
||||
detailButton->setFixedSize(QSize(20, 20));
|
||||
removeButton->setText(QStringLiteral("¡Á"));
|
||||
removeButton->setFixedSize(QSize(20, 20));
|
||||
const QString styleDisplayName = style->getDisplayName();
|
||||
|
||||
connect(detailButton, &QPushButton::clicked,
|
||||
[this, styleDisplayName]
|
||||
{
|
||||
const auto targetStyle = this->styleContainer->getStyle(styleDisplayName);
|
||||
auto* dialog = new LayerStyleDialog(this->styleContainer, targetStyle, this);
|
||||
dialog->exec();
|
||||
|
||||
if (dialog->layerStyle)
|
||||
{
|
||||
this->styleContainer->overrideStyle(dialog->layerStyle);
|
||||
this->styleContainer->computeNewHash();
|
||||
emit editLayerStyle(targetStyle);
|
||||
}
|
||||
});
|
||||
|
||||
connect(removeButton, &QPushButton::clicked,
|
||||
[this, styleDisplayName]
|
||||
{
|
||||
emit removeLayerStyle(styleDisplayName);
|
||||
});
|
||||
|
||||
QWidget* styleDisplayWidget = style->getListDisplayWidget();
|
||||
styleDisplayWidget->setParent(w);
|
||||
styleDisplayWidget->setSizePolicy(QSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding));
|
||||
|
||||
layout->addWidget(styleDisplayWidget);
|
||||
layout->addWidget(detailButton);
|
||||
layout->addWidget(removeButton);
|
||||
w->setLayout(layout);
|
||||
return w;
|
||||
}
|
|
@ -0,0 +1,35 @@
|
|||
#pragma once
|
||||
#include <map>
|
||||
#include <QListWidget>
|
||||
#include <qtmaterialraisedbutton.h>
|
||||
#include "LayerStyle.h"
|
||||
|
||||
class LayerContainerListWidget : public QListWidget
|
||||
{
|
||||
Q_OBJECT
|
||||
using PLayerStyleContainer = LayerStyleContainer*;
|
||||
private:
|
||||
QWidget* headerWidget;
|
||||
QPushButton* addButton;
|
||||
PLayerStyleContainer styleContainer;
|
||||
std::map<QString, QListWidgetItem*> styleItemMap;
|
||||
|
||||
void initHeader();
|
||||
void resetAddButton();
|
||||
QWidget* buildStyleListWidget(std::shared_ptr<LayerStyle> style);
|
||||
|
||||
public:
|
||||
LayerContainerListWidget(QWidget* parent = nullptr, const PLayerStyleContainer& styleContainer = nullptr);
|
||||
void setStyleContainer(const PLayerStyleContainer& styleContainer, bool forceRefresh = false);
|
||||
PLayerStyleContainer getStyleContainer() const;
|
||||
|
||||
protected slots:
|
||||
void onAddLayerStyle(const std::shared_ptr<LayerStyle>& style);
|
||||
void onRemoveLayerStyle(const QString& styleName);
|
||||
|
||||
signals:
|
||||
void addLayerStyle(const std::shared_ptr<LayerStyle>& style);
|
||||
void editLayerStyle(const std::shared_ptr<LayerStyle>& style);
|
||||
void removeLayerStyle(const QString& styleName);
|
||||
};
|
||||
|
|
@ -4,10 +4,10 @@
|
|||
#include <QGridLayout>
|
||||
|
||||
LayerStyleDialog::LayerStyleDialog(
|
||||
LayerStyleContainer& styles,
|
||||
LayerStyleContainer* pStyles,
|
||||
const std::shared_ptr<LayerStyle>& existedStyle,
|
||||
QWidget* parent
|
||||
) : QDialog(parent), styles(&styles)
|
||||
) : QDialog(parent), styles(pStyles)
|
||||
{
|
||||
dialogLayout = new QGridLayout;
|
||||
dialogLayout->setAlignment(Qt::AlignmentFlag::AlignHCenter);
|
||||
|
@ -23,13 +23,13 @@ LayerStyleDialog::LayerStyleDialog(
|
|||
}
|
||||
else
|
||||
{
|
||||
QStringList unusedStyleNames = styles.unusedStyleNames();
|
||||
QStringList unusedStyleNames = styles->unusedStyleNames();
|
||||
auto* typeSelector = new QComboBox(this);
|
||||
|
||||
if (!unusedStyleNames.empty())
|
||||
{
|
||||
typeSelector->addItems(unusedStyleNames);
|
||||
this->modifyingStyle = std::move(styles.makeUnusedStyle(unusedStyleNames[0]));
|
||||
this->modifyingStyle = std::move(styles->makeUnusedStyle(unusedStyleNames[0]));
|
||||
|
||||
dialogLayout->addWidget(typeSelector, 0, 0);
|
||||
|
||||
|
|
|
@ -13,7 +13,7 @@ private:
|
|||
std::unique_ptr<LayerStyle> modifyingStyle;
|
||||
public:
|
||||
LayerStyleDialog(
|
||||
LayerStyleContainer& styles,
|
||||
LayerStyleContainer* pStyles,
|
||||
const std::shared_ptr<LayerStyle>& existedStyle = nullptr,
|
||||
QWidget* parent = nullptr
|
||||
);
|
||||
|
|
|
@ -1,108 +0,0 @@
|
|||
#include "StrokeStyleListView.h"
|
||||
#include "ColorPicker.h"
|
||||
#include <qtmaterialraisedbutton.h>
|
||||
|
||||
constexpr int COLUMN_WIDTH = 0;
|
||||
constexpr int COLUMN_COLOR = 1;
|
||||
constexpr int COLUMN_METALLIC = 2;
|
||||
constexpr int COLUMN_ROUGHNESS = 3;
|
||||
constexpr int COLUMN_OPERATIONS = 4;
|
||||
|
||||
// TODO: 将这个类改为继承QWidget,把table转为其中的一个元素,加上新增行按钮和宽度设置
|
||||
StrokeStyleListView::StrokeStyleListView(
|
||||
std::shared_ptr<Renderer::StrokeRadialGradient> stroke,
|
||||
QWidget* parent
|
||||
) : QTableWidget(parent), stroke(stroke)
|
||||
{
|
||||
this->setSizeAdjustPolicy(QAbstractScrollArea::AdjustToContentsOnFirstShow);
|
||||
this->setColumnCount(5);
|
||||
this->setRowCount(stroke->materialMap.size());
|
||||
QStringList headers;
|
||||
headers.append(QStringLiteral("离心距离占比"));
|
||||
headers.append(QStringLiteral("颜色"));
|
||||
headers.append(QStringLiteral("金属度"));
|
||||
headers.append(QStringLiteral("粗糙度"));
|
||||
headers.append(QStringLiteral("其他操作"));
|
||||
this->setHorizontalHeaderLabels(headers);
|
||||
for (int row = 0; auto& strokePair : stroke->materialMap)
|
||||
{
|
||||
QTableWidgetItem* widthItem = new QTableWidgetItem;
|
||||
widthItem->setData(Qt::EditRole, strokePair.first);
|
||||
this->setItem(row, COLUMN_WIDTH, widthItem);
|
||||
|
||||
QColor* colorPtr = &(strokePair.second.color);
|
||||
QTableWidgetItem* colorItem = new QTableWidgetItem;
|
||||
colorItem->setData(Qt::DisplayRole, *colorPtr);
|
||||
this->setItem(row, COLUMN_COLOR, colorItem);
|
||||
ColorPicker* colorPicker = new ColorPicker(*colorPtr, this);
|
||||
this->setCellWidget(row, COLUMN_COLOR, colorPicker);
|
||||
connect(colorPicker, &ColorPicker::colorChanged, [this, colorPtr](QColor color) {
|
||||
*colorPtr = color;
|
||||
this->update();
|
||||
});
|
||||
|
||||
QTableWidgetItem* metallicItem = new QTableWidgetItem;
|
||||
metallicItem->setData(Qt::EditRole, strokePair.second.metallic);
|
||||
this->setItem(row, COLUMN_METALLIC, metallicItem);
|
||||
|
||||
QTableWidgetItem* roughnessItem = new QTableWidgetItem;
|
||||
roughnessItem->setData(Qt::EditRole, strokePair.second.roughness);
|
||||
this->setItem(row, COLUMN_ROUGHNESS, roughnessItem);
|
||||
|
||||
QtMaterialRaisedButton* removeButton = new QtMaterialRaisedButton("-", this);
|
||||
removeButton->setFixedSize(20, 20);
|
||||
this->setCellWidget(row, COLUMN_OPERATIONS, removeButton);
|
||||
connect(removeButton, &QtMaterialRaisedButton::clicked, [this, row]() {
|
||||
this->stroke->materialMap.erase(this->item(row, COLUMN_WIDTH)->text().toFloat());
|
||||
this->removeRow(row);
|
||||
});
|
||||
|
||||
row++;
|
||||
}
|
||||
connect(this, &StrokeStyleListView::currentItemChanged, this, &StrokeStyleListView::onCurrentItemChanged);
|
||||
connect(this, &StrokeStyleListView::cellChanged, this, &StrokeStyleListView::onCellChanged);
|
||||
this->adjustSize();
|
||||
}
|
||||
|
||||
void StrokeStyleListView::onCurrentItemChanged(QTableWidgetItem* current, QTableWidgetItem* previous)
|
||||
{
|
||||
if (!current) return;
|
||||
int column = current->column();
|
||||
if (column != COLUMN_COLOR && column != COLUMN_OPERATIONS)
|
||||
{
|
||||
this->currentItemValue = current->text();
|
||||
}
|
||||
}
|
||||
|
||||
void StrokeStyleListView::onCellChanged(int row, int column)
|
||||
{
|
||||
auto changedItem = this->item(row, column);
|
||||
auto changedItemValue = changedItem->text().toFloat();
|
||||
if (changedItemValue < 0 || 1 < changedItemValue)
|
||||
{
|
||||
changedItem->setData(Qt::EditRole, this->currentItemValue.toFloat());
|
||||
return;
|
||||
}
|
||||
auto changedWidth = this->item(row, COLUMN_WIDTH)->text().toFloat();
|
||||
switch (row)
|
||||
{
|
||||
case COLUMN_WIDTH:
|
||||
{
|
||||
float oldWidth = this->currentItemValue.toFloat();
|
||||
auto node = stroke->materialMap.extract(oldWidth);
|
||||
node.key() = changedWidth;
|
||||
stroke->materialMap.insert(std::move(node));
|
||||
break;
|
||||
}
|
||||
case COLUMN_METALLIC:
|
||||
{
|
||||
stroke->materialMap[changedWidth].metallic = changedItemValue;
|
||||
break;
|
||||
}
|
||||
case COLUMN_ROUGHNESS:
|
||||
{
|
||||
stroke->materialMap[changedWidth].roughness = changedItemValue;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,21 +0,0 @@
|
|||
#pragma once
|
||||
#include "LayerStyle.h"
|
||||
#include "../Renderer/Painting/MaterialStyleStroke.h"
|
||||
#include <QListView>
|
||||
#include <QListWidget>
|
||||
#include <QTableWidget>
|
||||
class StrokeStyleListView : public QTableWidget
|
||||
{
|
||||
Q_OBJECT
|
||||
private:
|
||||
QString currentItemValue;
|
||||
|
||||
public:
|
||||
StrokeStyleListView(std::shared_ptr<Renderer::StrokeRadialGradient> stroke, QWidget* parent = nullptr);
|
||||
std::shared_ptr<Renderer::StrokeRadialGradient> stroke;
|
||||
|
||||
protected slots:
|
||||
void onCurrentItemChanged(QTableWidgetItem* current, QTableWidgetItem* previous);
|
||||
void onCellChanged(int row, int column);
|
||||
};
|
||||
|
|
@ -17,9 +17,9 @@ EditorWidgetItem::EditorWidgetItem(QString filePath,QWidget *parent) : QWidget(p
|
|||
treeWidget = ui.LayerTree;
|
||||
tabWidget = ui.DisplayTab;
|
||||
this->filePath = filePath;
|
||||
elementInfoDisplayWidget = ui.ElementDisplay;
|
||||
layerInfoDisplayWidget = dynamic_cast<InfoDisplayWidget*>(tabWidget->widget(0));
|
||||
elementInfoDisplayWidget = dynamic_cast<ElementPoolWidget *>(tabWidget->widget(1));
|
||||
editorSettingWidget = dynamic_cast<EditorSettingWidget*>(tabWidget->widget(2));
|
||||
editorSettingWidget = dynamic_cast<EditorSettingWidget*>(tabWidget->widget(1));
|
||||
elementInfoDisplayWidget->enableEdit();
|
||||
qDebug() << layerInfoDisplayWidget;
|
||||
qDebug() << elementInfoDisplayWidget;
|
||||
|
|
|
@ -9,6 +9,7 @@
|
|||
#include <QLabel>
|
||||
#include <QObject>
|
||||
#include <QDebug>
|
||||
#include <QListView>
|
||||
#define _USE_JOIN_VIEW_INPUT_RANGE
|
||||
#include <QJsonArray>
|
||||
#include <ranges>
|
||||
|
@ -193,6 +194,16 @@ bool LayerStyleContainer::useStyle(const std::shared_ptr<LayerStyle>& style)
|
|||
return true;
|
||||
}
|
||||
|
||||
bool LayerStyleContainer::overrideStyle(const std::shared_ptr<LayerStyle>& style)
|
||||
{
|
||||
if (!styles.contains(style->getDisplayName()))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
styles[style->getDisplayName()] = style;
|
||||
return true;
|
||||
}
|
||||
|
||||
bool LayerStyleContainer::dropStyle(const QString& styleName)
|
||||
{
|
||||
auto styleNode = usedStyles.extract(styleName);
|
||||
|
@ -205,6 +216,11 @@ bool LayerStyleContainer::dropStyle(const QString& styleName)
|
|||
return true;
|
||||
}
|
||||
|
||||
std::shared_ptr<LayerStyle> LayerStyleContainer::getStyle(const QString& styleName) const
|
||||
{
|
||||
return styles.at(styleName);
|
||||
}
|
||||
|
||||
float LayerStyleContainer::boundingBoxAffectValue() const {
|
||||
float maxLineWidth = 0;
|
||||
const auto strokeStyle = styles.find(StrokeElementLayerStyle::displayName());
|
||||
|
@ -234,6 +250,15 @@ size_t LayerStyleContainer::getHash() const
|
|||
return hash;
|
||||
}
|
||||
|
||||
bool LayerStyleContainer::operator==(const LayerStyleContainer& other) const
|
||||
{
|
||||
if (getHash() != other.getHash() || unusedStyleNames() != other.unusedStyleNames())
|
||||
{
|
||||
return false;
|
||||
}
|
||||
return std::ranges::equal(styles | std::views::values, other.styles | std::views::values);
|
||||
}
|
||||
|
||||
std::unique_ptr<StrokeElementLayerStyle> StrokeElementLayerStyle::fromJson(const QJsonObject& json)
|
||||
{
|
||||
auto ptr = std::make_unique<StrokeElementLayerStyle>(
|
||||
|
@ -298,6 +323,20 @@ std::unique_ptr<LayerStyle> StrokeElementLayerStyle::clone() const
|
|||
return std::make_unique<StrokeElementLayerStyle>(StrokeElementLayerStyle(*this));
|
||||
}
|
||||
|
||||
bool StrokeElementLayerStyle::operator==(const LayerStyle& other) const
|
||||
{
|
||||
if (!LayerStyle::operator==(other))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
const auto otherStyle = dynamic_cast<const StrokeElementLayerStyle*>(&other);
|
||||
if (!otherStyle)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
return this->strokePair.first == otherStyle->strokePair.first && this->strokePair.second == otherStyle->strokePair.second;
|
||||
}
|
||||
|
||||
std::unique_ptr<FillElementLayerStyle> FillElementLayerStyle::fromJson(const QJsonObject& json)
|
||||
{
|
||||
auto ptr = std::make_unique<FillElementLayerStyle>(
|
||||
|
@ -359,6 +398,20 @@ std::unique_ptr<LayerStyle> FillElementLayerStyle::clone() const
|
|||
return std::make_unique<FillElementLayerStyle>(FillElementLayerStyle(*this));
|
||||
}
|
||||
|
||||
bool FillElementLayerStyle::operator==(const LayerStyle& other) const
|
||||
{
|
||||
if (!LayerStyle::operator==(other))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
const auto otherStyle = dynamic_cast<const FillElementLayerStyle*>(&other);
|
||||
if (!otherStyle)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
return this->fillMaterialStyle == otherStyle->fillMaterialStyle;
|
||||
}
|
||||
|
||||
std::unique_ptr<LayerStyle> LayerStyle::fromJson(const QJsonObject& json)
|
||||
{
|
||||
QString type = json["type"].toString();
|
||||
|
@ -379,3 +432,8 @@ QJsonObject LayerStyle::toJson() const
|
|||
json["type"] = this->getTypeName();
|
||||
return json;
|
||||
}
|
||||
|
||||
bool LayerStyle::operator==(const LayerStyle& other) const
|
||||
{
|
||||
return this->getTypeName() == other.getTypeName();
|
||||
}
|
||||
|
|
|
@ -3,7 +3,6 @@
|
|||
#include <utility>
|
||||
#include <set>
|
||||
#include <map>
|
||||
#include <QListWidget>
|
||||
#include <QJsonObject>
|
||||
#include <QJsonArray>
|
||||
#include "../Renderer/Painting/ElementStyle.h"
|
||||
|
@ -36,6 +35,8 @@ public:
|
|||
|
||||
virtual QJsonObject toJson() const;
|
||||
virtual std::unique_ptr<LayerStyle> clone() const = 0;
|
||||
|
||||
virtual bool operator==(const LayerStyle& other) const;
|
||||
};
|
||||
|
||||
class StrokeElementLayerStyle : public LayerStyle
|
||||
|
@ -57,6 +58,8 @@ public:
|
|||
QJsonObject toJson() const override;
|
||||
std::unique_ptr<LayerStyle> clone() const override;
|
||||
|
||||
bool operator==(const LayerStyle& other) const override;
|
||||
|
||||
std::pair<PMaterialStyleStroke, PMaterialStyleStroke> strokePair;
|
||||
bool enableEachSideIndependent = false;
|
||||
};
|
||||
|
@ -79,6 +82,8 @@ public:
|
|||
QJsonObject toJson() const override;
|
||||
std::unique_ptr<LayerStyle> clone() const override;
|
||||
|
||||
bool operator==(const LayerStyle& other) const override;
|
||||
|
||||
PMaterialStyleFill fillMaterialStyle;
|
||||
};
|
||||
|
||||
|
@ -125,10 +130,14 @@ public:
|
|||
QStringList unusedStyleNames() const;
|
||||
std::unique_ptr<LayerStyle> makeUnusedStyle(const QString& styleName) const;
|
||||
bool useStyle(const std::shared_ptr<LayerStyle>& style);
|
||||
bool overrideStyle(const std::shared_ptr<LayerStyle>& style);
|
||||
bool dropStyle(const QString& styleName);
|
||||
std::shared_ptr<LayerStyle> getStyle(const QString& styleName) const;
|
||||
float boundingBoxAffectValue() const;
|
||||
size_t getHash() const;
|
||||
|
||||
bool operator==(const LayerStyleContainer& other) const;
|
||||
|
||||
/**
|
||||
* 需要在每次更改后手动调用
|
||||
*/
|
||||
|
|
|
@ -2,12 +2,7 @@
|
|||
#include "./EditorWidgetComponent/LayerStyleDialog.h"
|
||||
#include <QLineEdit>
|
||||
#include <QTextBlock>
|
||||
#include <QListWidget>
|
||||
#include <QDialog>
|
||||
#include <QComboBox>
|
||||
#include <qtmaterialraisedbutton.h>
|
||||
#include <qtmaterialflatbutton.h>
|
||||
#include <QLabel>
|
||||
#include <QCheckBox>
|
||||
|
||||
void InfoDisplayWidget::setLayer(LayerWrapper *layer)
|
||||
|
@ -27,6 +22,7 @@ InfoDisplayWidget::InfoDisplayWidget(QWidget* parent) :QWidget(parent)
|
|||
ui.scaleX->setLabel(("水平缩放"));
|
||||
ui.scaleY->setLabel(("垂直缩放"));
|
||||
ui.rotation->setValidator(new QIntValidator(-10000, 10000, this));
|
||||
ui.styleList->setDisabled(true);
|
||||
connect(ui.rotation, &QLineEdit::textChanged, [=](QString content) {
|
||||
this->displayLayer->property.rotation = content.toDouble();
|
||||
emit triggerCentralRefresh();
|
||||
|
@ -59,6 +55,15 @@ InfoDisplayWidget::InfoDisplayWidget(QWidget* parent) :QWidget(parent)
|
|||
this->displayLayer->property.flipY = state;
|
||||
emit triggerCentralRefresh();
|
||||
});
|
||||
connect(ui.styleList, &LayerContainerListWidget::addLayerStyle, [this](const std::shared_ptr<LayerStyle>& style) {
|
||||
emit triggerCentralRefresh();
|
||||
});
|
||||
connect(ui.styleList, &LayerContainerListWidget::editLayerStyle, [this](const std::shared_ptr<LayerStyle>& style) {
|
||||
emit triggerCentralRefresh();
|
||||
});
|
||||
connect(ui.styleList, &LayerContainerListWidget::removeLayerStyle, [this](const QString& styleName) {
|
||||
emit triggerCentralRefresh();
|
||||
});
|
||||
}
|
||||
|
||||
void InfoDisplayWidget::setVisiable(bool visiable)
|
||||
|
@ -79,5 +84,14 @@ void InfoDisplayWidget::refresh()
|
|||
ui.scaleY->setText(QString::number(this->displayLayer->property.scale.y()));
|
||||
ui.flipX->setChecked(this->displayLayer->property.flipX);
|
||||
ui.flipY->setChecked(this->displayLayer->property.flipY);
|
||||
if (this->displayLayer->canApplyStyles())
|
||||
{
|
||||
ui.styleList->setDisabled(false);
|
||||
ui.styleList->setStyleContainer(&static_cast<LeafLayerWrapper*>(this->displayLayer)->styles);
|
||||
}
|
||||
else
|
||||
{
|
||||
ui.styleList->setDisabled(true);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,8 +1,5 @@
|
|||
#pragma once
|
||||
#include "GraphicElement.h"
|
||||
#include "LayerWrapper.h"
|
||||
#include <QFormLayout>
|
||||
#include <QLabel>
|
||||
#include <QWidget>
|
||||
#include "ElementPoolWidget.h"
|
||||
#include "ui_EditorLayerInfoWidget.h"
|
||||
|
|
Loading…
Reference in New Issue