Commit 56c06d8b authored by Inge Wallin's avatar Inge Wallin

Refactor: Move class ItemGroup into its own file

parent de2f77dc
......@@ -5,7 +5,7 @@ values in the other classes.
Legend
* ClassName{filename} Short explanation
[=0] This class contains pure virtual member functions.
[=0] This class has pure virtual member functions.
* subclass
[important members]
......@@ -23,6 +23,7 @@ Legend
* CGConstraintSolver
[]
* Solver Generic Solver interface
[=0]
* GenericEulerSolver Solver of ordinary diff equations
* EulerSolver
* AdaptiveEulerSolver
......@@ -33,9 +34,10 @@ Legend
* Item{item.h} Root class for world items (bodies, forces)
[world, group, objectErrors, color]
* NoteImage Image embedded in a Note
* NoteImage{tool.h} Image embedded in a Note
* NoteFormula LaTeX formula embedded in a Note
* ItemGroup
* ItemGroup{itemgroup.h}
[items]
* Gas Group of GasParticle and a Force
* SoftBody Group of SoftBodyParticles and SoftBodySprings
......@@ -56,7 +58,7 @@ Legend
* Force Anything that acts upon bodies changing
derivatives of dynamic variables
[=0] derivatives of dynamic variables
* CoulombForce Force for charged particles.
* GasLJForce Force within gasses
* GravitationForce Force between particles
......@@ -68,7 +70,7 @@ Legend
* Joint
[]
[=0]
* Anchor Fixes the position of a body
* Pin Fixes the position of a a given point of a body to another body
* Stick Fixed distance between two points on particles or rigid bodies
......@@ -88,7 +90,7 @@ Auxiliary classes
* Contact defines contact between two bodies
Used by CollisionSolver.
* ConstraintsInfo{world.h} defines ...
* ConstraintsInfo{world.h} defines constraints between objects
Used by ConstraintSolver
[...]
......
......@@ -9,6 +9,7 @@ set(stepcore_SRCS
objecterrors.cc
force.cc
joint.cc
itemgroup.cc
# Storage objects
world.cc
......
/* This file is part of StepCore library.
Copyright (C) 2007 Vladimir Kuznetsov <ks.vladimir@gmail.com>
Copyright (C) 2014 Inge Wallin <inge@lysator.liu.se>
StepCore library 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 2 of the License, or
(at your option) any later version.
StepCore library 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 StepCore; if not, write to the Free Software
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
#include "itemgroup.h"
#include "world.h" // FIXME: This is ugly
namespace StepCore
{
STEPCORE_META_OBJECT(ItemGroup, QT_TRANSLATE_NOOP("ObjectClass", "ItemGroup"), QT_TR_NOOP("ItemGroup"),
0, STEPCORE_SUPER_CLASS(Item),)
ItemGroup::ItemGroup(const ItemGroup& group)
: Item()
{
*this = group;
}
void ItemGroup::setWorld(World* world)
{
ItemList::const_iterator end = _items.end();
for(ItemList::const_iterator it = _items.begin(); it != end; ++it)
(*it)->setWorld(world);
Item::setWorld(world);
}
void ItemGroup::worldItemRemoved(Item* item)
{
ItemList::const_iterator end = _items.end();
for(ItemList::const_iterator it = _items.begin(); it != end; ++it)
(*it)->worldItemRemoved(item);
}
void ItemGroup::addItem(Item* item)
{
_items.push_back(item);
if(world()) world()->worldItemAdded(item);
item->setGroup(this);
item->setWorld(this->world());
}
void ItemGroup::removeItem(Item* item)
{
item->setWorld(NULL);
item->setGroup(NULL);
if(world()) world()->worldItemRemoved(item);
ItemList::iterator i = std::find(_items.begin(), _items.end(), item);
STEPCORE_ASSERT_NOABORT(i != _items.end());
_items.erase(i);
}
void ItemGroup::clear()
{
ItemList::const_iterator end = _items.end();
for(ItemList::const_iterator it = _items.begin(); it != end; ++it) {
(*it)->setWorld(NULL);
(*it)->setGroup(NULL);
if(world()) world()->worldItemRemoved(*it);
}
for(ItemList::const_iterator it = _items.begin(); it != end; ++it) {
delete *it;
}
_items.clear();
}
ItemGroup::~ItemGroup()
{
clear();
}
ItemGroup& ItemGroup::operator=(const ItemGroup& group)
{
/*
item->setGroup(this);
item->setWorld(this->world());
_items.push_back(item);
if(world()) {
//world()->worldItemAdded(item);
ItemGroup* gr = dynamic_cast<ItemGroup*>(item);
if(gr) gr->groupItemsAdded();
}
*/
if(this == &group) return *this;
clear();
_items.reserve(group._items.size());
const ItemList::const_iterator gr_end = group._items.end();
for(ItemList::const_iterator it = group._items.begin(); it != gr_end; ++it) {
StepCore::Item* item = static_cast<Item*>( (*it)->metaObject()->cloneObject(*(*it)) );
_items.push_back(item);
}
const ItemList::const_iterator end = _items.end();
for(ItemList::const_iterator it = _items.begin(); it != end; ++it) {
(*it)->setGroup(this);
}
Item::operator=(group);
// NOTE: We don't change world() here
return *this;
}
int ItemGroup::childItemIndex(const Item* item) const
{
ItemList::const_iterator o = std::find(_items.begin(), _items.end(), item);
STEPCORE_ASSERT_NOABORT(o != _items.end());
return std::distance(_items.begin(), o);
}
Item* ItemGroup::childItem(const QString& name) const
{
ItemList::const_iterator end = _items.end();
for(ItemList::const_iterator it = _items.begin(); it != end; ++it)
if((*it)->name() == name) return *it;
return NULL;
}
Item* ItemGroup::item(const QString& name) const
{
if(name.isEmpty()) return NULL;
ItemList::const_iterator end = _items.end();
for(ItemList::const_iterator it = _items.begin(); it != end; ++it) {
if((*it)->name() == name) return *it;
if((*it)->metaObject()->inherits<ItemGroup>()) {
Item* ret = static_cast<ItemGroup*>(*it)->item(name);
if(ret) return ret;
}
}
return NULL;
}
void ItemGroup::allItems(ItemList* items) const
{
items->reserve(_items.size());
ItemList::const_iterator end = _items.end();
for(ItemList::const_iterator it = _items.begin(); it != end; ++it) {
items->push_back(*it);
if((*it)->metaObject()->inherits<ItemGroup>())
static_cast<ItemGroup*>(*it)->allItems(items);
}
}
} // namespace StepCore
/* This file is part of StepCore library.
Copyright (C) 2007 Vladimir Kuznetsov <ks.vladimir@gmail.com>
Copyright (C) 2014 Inge Wallin <inge@lysator.liu.se>
StepCore library 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 2 of the License, or
(at your option) any later version.
StepCore library 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 StepCore; if not, write to the Free Software
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
/** \file itemgroup.h
* \brief Contains the ItemGroup object.
*/
#ifndef STEPCORE_ITEMGROUP_H
#define STEPCORE_ITEMGROUP_H
#include <vector> // XXX: Replace if Qt is enabled.
#include "types.h"
#include "item.h"
namespace StepCore
{
/** \ingroup world
* \brief Groups several items together
*/
class ItemGroup : public Item
{
STEPCORE_OBJECT(ItemGroup)
public:
/** Constructs empty group */
ItemGroup(const QString& name = QString()) : Item(name) {}
/** Constructs a copy of the group (deep copy) */
ItemGroup(const ItemGroup& group);
/** Destroys the group and all its subitems */
~ItemGroup();
/** Assignment operator (deep copy)
* \warning Do not call this on groups already attached to the world */
ItemGroup& operator=(const ItemGroup& group);
/** Get list of all direct child items in the ItemGroup */
const ItemList& items() const { return _items; }
/** Get list of all items in the ItemGroup
* \note This operation takes long time since it
* recursively traverses all child groups */
ItemList allItems() const { ItemList l; allItems(&l); return l; }
/** Get list of all items in the ItemGroup
* \param items Array to store items
* \note This operation takes long time since it
* recursively traverses all child groups */
void allItems(ItemList* items) const;
/** Add new item to the group */
virtual void addItem(Item* item);
/** Remove item from the group (you should delete item youself) */
virtual void removeItem(Item* item);
/** Delete item from the group (it actually deletes item) */
virtual void deleteItem(Item* item) { removeItem(item); delete item; }
/** Deletes all items */
void clear();
/** Finds direct child item in items() */
int childItemIndex(const Item* item) const;
/** Get direct child count */
int childItemCount() const { return _items.size(); }
/** Get direct child item by its index */
Item* childItem(int index) const { return _items[index]; }
/** Get direct child item by its name */
Item* childItem(const QString& name) const;
/** Get any descendant item by its name */
Item* item(const QString& name) const;
/** Recursively call setWorld for all children objects */
void setWorld(World* world);
/** Recursively call worldItemRemoved for all children objects */
void worldItemRemoved(Item* item);
private:
ItemList _items;
};
} // namespace StepCore
#endif
......@@ -31,157 +31,12 @@ namespace StepCore
STEPCORE_META_OBJECT(Tool, QT_TRANSLATE_NOOP("ObjectClass", "Tool"), QT_TR_NOOP("Tool"), MetaObject::ABSTRACT,,)
STEPCORE_META_OBJECT(ItemGroup, QT_TRANSLATE_NOOP("ObjectClass", "ItemGroup"), QT_TR_NOOP("ItemGroup"), 0, STEPCORE_SUPER_CLASS(Item),)
STEPCORE_META_OBJECT(World, QT_TRANSLATE_NOOP("ObjectClass", "World"), QT_TR_NOOP("World"), 0, STEPCORE_SUPER_CLASS(ItemGroup),
STEPCORE_PROPERTY_RW_D(double, time, QT_TRANSLATE_NOOP("PropertyName", "time"), QT_TRANSLATE_NOOP("Units", "s"), QT_TR_NOOP("Current time"), time, setTime)
STEPCORE_PROPERTY_RW (double, timeScale, QT_TR_NOOP("timeScale"), STEPCORE_UNITS_1, QT_TR_NOOP("Simulation speed scale"), timeScale, setTimeScale)
STEPCORE_PROPERTY_RW (bool, errorsCalculation, QT_TR_NOOP("errorsCalculation"), STEPCORE_UNITS_NULL,
QT_TR_NOOP("Enable global error calculation"), errorsCalculation, setErrorsCalculation))
ItemGroup::ItemGroup(const ItemGroup& group)
: Item()
{
*this = group;
}
void ItemGroup::setWorld(World* world)
{
ItemList::const_iterator end = _items.end();
for(ItemList::const_iterator it = _items.begin(); it != end; ++it)
(*it)->setWorld(world);
Item::setWorld(world);
}
void ItemGroup::worldItemRemoved(Item* item)
{
ItemList::const_iterator end = _items.end();
for(ItemList::const_iterator it = _items.begin(); it != end; ++it)
(*it)->worldItemRemoved(item);
}
void ItemGroup::addItem(Item* item)
{
_items.push_back(item);
if(world()) world()->worldItemAdded(item);
item->setGroup(this);
item->setWorld(this->world());
}
void ItemGroup::removeItem(Item* item)
{
item->setWorld(NULL);
item->setGroup(NULL);
if(world()) world()->worldItemRemoved(item);
ItemList::iterator i = std::find(_items.begin(), _items.end(), item);
STEPCORE_ASSERT_NOABORT(i != _items.end());
_items.erase(i);
}
void ItemGroup::clear()
{
ItemList::const_iterator end = _items.end();
for(ItemList::const_iterator it = _items.begin(); it != end; ++it) {
(*it)->setWorld(NULL);
(*it)->setGroup(NULL);
if(world()) world()->worldItemRemoved(*it);
}
for(ItemList::const_iterator it = _items.begin(); it != end; ++it) {
delete *it;
}
_items.clear();
}
ItemGroup::~ItemGroup()
{
clear();
}
ItemGroup& ItemGroup::operator=(const ItemGroup& group)
{
/*
item->setGroup(this);
item->setWorld(this->world());
_items.push_back(item);
if(world()) {
//world()->worldItemAdded(item);
ItemGroup* gr = dynamic_cast<ItemGroup*>(item);
if(gr) gr->groupItemsAdded();
}
*/
if(this == &group) return *this;
clear();
_items.reserve(group._items.size());
const ItemList::const_iterator gr_end = group._items.end();
for(ItemList::const_iterator it = group._items.begin(); it != gr_end; ++it) {
StepCore::Item* item = static_cast<Item*>( (*it)->metaObject()->cloneObject(*(*it)) );
_items.push_back(item);
}
const ItemList::const_iterator end = _items.end();
for(ItemList::const_iterator it = _items.begin(); it != end; ++it) {
(*it)->setGroup(this);
}
Item::operator=(group);
// NOTE: We don't change world() here
return *this;
}
int ItemGroup::childItemIndex(const Item* item) const
{
ItemList::const_iterator o = std::find(_items.begin(), _items.end(), item);
STEPCORE_ASSERT_NOABORT(o != _items.end());
return std::distance(_items.begin(), o);
}
Item* ItemGroup::childItem(const QString& name) const
{
ItemList::const_iterator end = _items.end();
for(ItemList::const_iterator it = _items.begin(); it != end; ++it)
if((*it)->name() == name) return *it;
return NULL;
}
Item* ItemGroup::item(const QString& name) const
{
if(name.isEmpty()) return NULL;
ItemList::const_iterator end = _items.end();
for(ItemList::const_iterator it = _items.begin(); it != end; ++it) {
if((*it)->name() == name) return *it;
if((*it)->metaObject()->inherits<ItemGroup>()) {
Item* ret = static_cast<ItemGroup*>(*it)->item(name);
if(ret) return ret;
}
}
return NULL;
}
void ItemGroup::allItems(ItemList* items) const
{
items->reserve(_items.size());
ItemList::const_iterator end = _items.end();
for(ItemList::const_iterator it = _items.begin(); it != end; ++it) {
items->push_back(*it);
if((*it)->metaObject()->inherits<ItemGroup>())
static_cast<ItemGroup*>(*it)->allItems(items);
}
}
void ConstraintsInfo::setDimension(int newVariablesCount, int newConstraintsCount, int newContactsCount)
{
// std::cerr << " ConstraintsInfo::setDimension("
......
......@@ -39,6 +39,7 @@
#include "body.h"
#include "force.h"
#include "joint.h"
#include "itemgroup.h"
// TODO: split this file
......@@ -49,7 +50,6 @@ namespace StepCore
class World;
class Solver;
class Item;
class ItemGroup;
class CollisionSolver;
class ConstraintSolver;
......@@ -67,68 +67,6 @@ public:
virtual ~Tool() {}
};
/** \ingroup world
* \brief Groups several items together
*/
class ItemGroup : public Item
{
STEPCORE_OBJECT(ItemGroup)
public:
/** Constructs empty group */
ItemGroup(const QString& name = QString()) : Item(name) {}
/** Constructs a copy of the group (deep copy) */
ItemGroup(const ItemGroup& group);
/** Destroys the group and all its subitems */
~ItemGroup();
/** Assignment operator (deep copy)
* \warning Do not call this on groups already attached to the world */
ItemGroup& operator=(const ItemGroup& group);
/** Get list of all direct child items in the ItemGroup */
const ItemList& items() const { return _items; }
/** Get list of all items in the ItemGroup
* \note This operation takes long time since it
* recursively traverses all child groups */
ItemList allItems() const { ItemList l; allItems(&l); return l; }
/** Get list of all items in the ItemGroup
* \param items Array to store items
* \note This operation takes long time since it
* recursively traverses all child groups */
void allItems(ItemList* items) const;
/** Add new item to the group */
virtual void addItem(Item* item);
/** Remove item from the group (you should delete item youself) */
virtual void removeItem(Item* item);
/** Delete item from the group (it actually deletes item) */
virtual void deleteItem(Item* item) { removeItem(item); delete item; }
/** Deletes all items */
void clear();
/** Finds direct child item in items() */
int childItemIndex(const Item* item) const;
/** Get direct child count */
int childItemCount() const { return _items.size(); }
/** Get direct child item by its index */
Item* childItem(int index) const { return _items[index]; }
/** Get direct child item by its name */
Item* childItem(const QString& name) const;
/** Get any descendant item by its name */
Item* item(const QString& name) const;
/** Recursively call setWorld for all children objects */
void setWorld(World* world);
/** Recursively call worldItemRemoved for all children objects */
void worldItemRemoved(Item* item);
private:
ItemList _items;
};
/** \ingroup world
* \brief Contains multiple Item, Solver and general properties such as time
* \todo Redesign to avoid variable copying (scatter/gatherVariables)
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment