Wed, 08 Jun 2022 19:33:00 +0300
Concentrate model editing into one coroutine inside main()
/* * LDForge: LDraw parts authoring CAD * Copyright (C) 2013 - 2020 Teemu Piippo * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see <http://www.gnu.org/licenses/>. */ #pragma once #include <QAbstractListModel> #include <memory> #include "main.h" #include "colors.h" struct SubfileReference { QString name; glm::mat4 transformation; bool inverted = false; }; template<typename T> struct Colored : T { ldraw::Color color; }; struct Comment { QString text; }; struct ParseError { QString code; }; struct Empty {}; using ModelElement = std::variant< Colored<SubfileReference>, Colored<LineSegment>, Colored<Triangle>, Colored<Quadrilateral>, Colored<ConditionalEdge>, Comment, Empty, ParseError>; QString modelElementToString(const ModelElement& element); struct ModelId { std::int32_t value; constexpr auto operator<=>(const ModelId& other) const = default; }; constexpr int qHash(ModelId id) { return qHash(id.value); } class Model : public QAbstractListModel { Q_OBJECT struct Entry { ModelElement data; ModelId id; }; std::vector<Entry> body; std::map<ModelId, int> positions; ModelId runningId = {1}; public: Model(QObject* parent); virtual ~Model(); ModelId append(const ModelElement& value); const ModelElement& at(int position) const; ModelId idAt(int position) const; void assignAt(int position, const ModelElement& element); std::optional<int> find(ModelId id) const; void remove(int index); int rowCount(const QModelIndex&) const override; QVariant data(const QModelIndex& index, int role) const override; const ModelElement& operator[](int index) const; int size() const; auto operator[](int index) { struct { Model& model; int index; operator const ModelElement&() { return model.at(index); } auto& operator=(const ModelElement& newData) { model.assignAt(index, newData); return *this; } const auto* operator&() { return &(this->operator const ModelElement&()); } } result{*this, index}; return result; } }; void save(const Model& model, QIODevice *device); void updateHeaderNameField(Model& model, const QString &name);