Sun, 29 Jan 2017 15:05:14 +0200
Major overhaul of object→document relationship: added the Model class which models the object buffer. Each object is to be included in a model (an invariant that currently does not hold). A document is a subclass of a model. The LDObject is also now agnostic about selection, and the selection is now a set. A lot of things are probably broken now but it's a major step forward.
The LDObject::destroy method is also now gone. The model decides when objects are destroyed and calls the destructor directly. The end result removes a lot of cruft and adds structure to LDObject relations.
Notes:
- Inlining does not currently work (nothing simply gets inlined in)
- More work is required to ensure that each object actually goes into a model
#pragma once #include "main.h" #include "ldObject.h" class Model { public: Model(); Model(const Model& other) = delete; ~Model(); virtual void addObject(LDObject* object); virtual void insertObject(int position, LDObject* object); virtual bool swapObjects(LDObject* one, LDObject* other); virtual bool setObjectAt(int idx, LDObject* obj); void removeAt(int position); void remove(LDObject* object); void replace(LDObject *object, Model& model); void clear(); void merge(Model& other, int position = -1); void replace(LDObject* object, LDObject* newObject); int size() const; const QVector<LDObject*>& objects() const; LDObject* getObject(int position) const; void recountTriangles(); int triangleCount() const; QVector<LDObject*>::iterator begin(); QVector<LDObject*>::iterator end(); template<typename T, typename... Args> T* emplace(Args&& ...args) { T* object = constructObject<T>(args...); addObject(object); return object; } template<typename T, typename... Args> T* emplaceAt(int position, Args&& ...args) { T* object = constructObject<T>(args...); insertObject(position, object); return object; } template<typename T, typename... Args> T* emplaceReplacement(LDObject* object, Args&& ...args) { if (object->model() == this) { int position = object->lineNumber(); T* replacement = constructObject<T>(args...); setObjectAt(position, replacement); return replacement; } else return nullptr; } protected: template<typename T, typename... Args> T* constructObject(Args&& ...args) { static_assert (std::is_base_of<LDObject, T>::value, "Can only use this function with LDObject-derivatives"); T* object = new T {args..., this}; // Set default color. Relying on virtual functions, this cannot be done in the c-tor. // TODO: store -1 as the default color if (object->isColored()) object->setColor(object->defaultColor()); return object; } void withdraw(LDObject* object); virtual LDObject* withdrawAt(int position); QVector<LDObject*> _objects; mutable int _triangleCount = 0; mutable bool _needsTriangleRecount; };