Commit c4190ece authored by Dirk Wilden's avatar Dirk Wilden

backup classes

git-svn-id: http://www.openflipper.org/svnrepo/OpenFlipper/branches/Free@11276 383ad7c9-94d9-4d36-a494-682f7c89f535
parent 8f58bde6
#include "BackupData.hh"
#define MAX_BACKUPS 20
//-----------------------------------------------------------------------------
BackupData::BackupData(BaseObjectData* _object) : currentState_(0), object_(_object)
{
}
//-----------------------------------------------------------------------------
BackupData::~BackupData(){
clear();
}
//-----------------------------------------------------------------------------
void BackupData::storeBackup(BaseBackup* _backup){
//store state
if ( currentState_ != 0 )
undoStates_.push_back( currentState_ );
currentState_ = _backup;
//clear redo states
while( !redoStates_.empty() ){
delete redoStates_.back();
redoStates_.pop_back();
}
//delete undo backups if there are too many
while( undoStates_.size() > MAX_BACKUPS ){
delete undoStates_.front();
undoStates_.erase( undoStates_.begin() );
}
}
//-----------------------------------------------------------------------------
void BackupData::undo(){
if ( undoStates_.empty() )
return;
//get backup
BaseBackup* backup = undoStates_.back();
//apply
backup->apply();
// update current state
undoStates_.pop_back();
redoStates_.push_back( currentState_ );
currentState_ = backup;
}
//-----------------------------------------------------------------------------
void BackupData::redo(){
if ( redoStates_.empty() )
return;
//get backup
BaseBackup* backup = redoStates_.back();
//apply
backup->apply();
// update current state
redoStates_.pop_back();
undoStates_.push_back( currentState_ );
currentState_ = backup;
}
//-----------------------------------------------------------------------------
QString BackupData::undoName(){
if ( undoStates_.empty() )
return QString();
return currentState_->name();
}
//-----------------------------------------------------------------------------
QString BackupData::redoName(){
if ( redoStates_.empty() )
return QString();
return redoStates_.back()->name();
}
//-----------------------------------------------------------------------------
int BackupData::undoID(){
if ( undoStates_.empty() )
return -1;
return undoStates_.back()->id();
}
//-----------------------------------------------------------------------------
int BackupData::redoID(){
if ( redoStates_.empty() )
return -1;
return redoStates_.back()->id();
}
//-----------------------------------------------------------------------------
int BackupData::currentID(){
if ( currentState_ == 0 )
return -1;
else
return currentState_->id();
}
//-----------------------------------------------------------------------------
bool BackupData::undoAvailable(){
return !undoStates_.empty();
}
//-----------------------------------------------------------------------------
bool BackupData::redoAvailable(){
return !redoStates_.empty();
}
//-----------------------------------------------------------------------------
bool BackupData::undoBlocked(){
if( !undoStates_.empty() )
return currentState_->blocked();
else
return false;
}
//-----------------------------------------------------------------------------
bool BackupData::redoBlocked(){
if( !redoStates_.empty() )
return redoStates_.back()->blocked();
else
return false;
}
//-----------------------------------------------------------------------------
void BackupData::clear(){
while( !undoStates_.empty() ){
delete undoStates_.back();
undoStates_.pop_back();
}
while( !redoStates_.empty() ){
delete redoStates_.back();
redoStates_.pop_back();
}
if ( currentState_ != 0 )
delete currentState_;
currentState_ = 0;
}
//-----------------------------------------------------------------------------
void BackupData::setLinks(IdList _objectIDs){
if ( currentState_ != 0 )
currentState_->setLinks(_objectIDs);
}
//-----------------------------------------------------------------------------
BaseBackup* BackupData::currentState(){
return currentState_;
}
//-----------------------------------------------------------------------------
/*===========================================================================*\
* *
* OpenFlipper *
* Copyright (C) 2001-2011 by Computer Graphics Group, RWTH Aachen *
* www.openflipper.org *
* *
*--------------------------------------------------------------------------- *
* This file is part of OpenFlipper. *
* *
* OpenFlipper is free software: you can redistribute it and/or modify *
* it under the terms of the GNU Lesser General Public License as *
* published by the Free Software Foundation, either version 3 of *
* the License, or (at your option) any later version with the *
* following exceptions: *
* *
* If other files instantiate templates or use macros *
* or inline functions from this file, or you compile this file and *
* link it with other files to produce an executable, this file does *
* not by itself cause the resulting executable to be covered by the *
* GNU Lesser General Public License. This exception does not however *
* invalidate any other reasons why the executable file might be *
* covered by the GNU Lesser General Public License. *
* *
* OpenFlipper 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 Lesser General Public License for more details. *
* *
* You should have received a copy of the GNU LesserGeneral Public *
* License along with OpenFlipper. If not, *
* see <http://www.gnu.org/licenses/>. *
* *
\*===========================================================================*/
/*===========================================================================*\
* *
* $Revision: 10745 $ *
* $LastChangedBy: moebius $ *
* $Date: 2011-01-26 10:23:50 +0100 (Wed, 26 Jan 2011) $ *
* *
\*===========================================================================*/
#ifndef BACKUPDATA_HH
#define BACKUPDATA_HH
#include <QString>
#include <OpenFlipper/common/perObjectData.hh>
#include <OpenFlipper/common/UpdateType.hh>
#include <OpenFlipper/common/BaseBackup.hh>
#define OBJECT_BACKUPS "Object Backups"
/**
* @brief Abstract class that is used to store backups
*
* The default implementation can only backup perObjectDatas
*/
class BackupData : public PerObjectData
{
public:
/// Constructor
BackupData(BaseObjectData* _object = 0);
/// Destructor
virtual ~BackupData();
public:
/// store a backup
void storeBackup(BaseBackup* _backup);
/// perform an undo if possible
void undo();
/// perform a redo if possible
void redo();
/// return the id of the next undo backup
int undoID();
/// return the id of the next redo backup
int redoID();
/// return the id of the current backup state
int currentID();
/// return the name of the next undo backup
QString undoName();
/// return the name of the next redo backup
QString redoName();
/// return if an undo backup is available
bool undoAvailable();
/// return if a redo backup is available
bool redoAvailable();
/// return if an undo backup is blocked
bool undoBlocked();
/// return if a redo backup is blocked
bool redoBlocked();
/// remove all backups
void clear();
/// add links to other backups for the current state
/// this is used to ensure that the backups are only applied simultaneously
void setLinks(IdList _objectIDs);
/// return the current state
BaseBackup* currentState();
protected:
std::vector< BaseBackup* > undoStates_;
std::vector< BaseBackup* > redoStates_;
BaseBackup* currentState_;
BaseObjectData* object_;
};
#endif //BACKUPDATA_HH
#include "BaseBackup.hh"
#include <OpenFlipper/common/BackupData.hh>
//-----------------------------------------------------------------------------
static int maxBackupId_ = 0;
//-----------------------------------------------------------------------------
BaseBackup::BaseBackup(QString _name) : object_(0), name_(_name), id_(maxBackupId_++)
{
}
//-----------------------------------------------------------------------------
BaseBackup::BaseBackup(BaseObjectData* _object, QString _name, UpdateType _type) : object_(_object), name_(_name), id_(maxBackupId_++)
{
// std::cerr << "Create BaseBackup with name:" << name_.toStdString() << "(id : " << id_ << ")" << std::endl;
// Get the per Object Datas
QMap<QString, PerObjectData*> dataMap = object_->getPerObjectDataMap();
// Iterate over all per Object datas and try to copy them into our backup storage
QMap<QString, PerObjectData*>::const_iterator mapIter;
for ( mapIter = dataMap.constBegin(); mapIter != dataMap.constEnd(); ++mapIter){
//don't copy myself
if ( mapIter.key() == OBJECT_BACKUPS ) continue;
// Try to get a copy of the objectData
PerObjectData* copiedData = mapIter.value()->copyPerObjectData();
if ( copiedData )
objectDatas_.push_back( std::make_pair( mapIter.key(),copiedData ) );
else
std::cerr << "Failed to copy per Object Data: " << mapIter.key().toStdString() << std::endl;
}
}
//-----------------------------------------------------------------------------
BaseBackup::~BaseBackup(){
// std::cerr << "Delete BaseBackup with name:" << name_.toStdString() << "(id : " << id_ << ")" << std::endl;
for (uint i=0; i < objectDatas_.size(); i++)
delete objectDatas_[i].second;
}
//-----------------------------------------------------------------------------
void BaseBackup::apply(){
// std::cerr << "Apply BaseBackup with name:" << name_.toStdString() << "(id : " << id_ << ")" << std::endl;
if (object_ == 0)
return;
PerObjectData* backupData = 0;
// Get the per Object Data container in the object
QMap<QString, PerObjectData*>& dataMap = object_->getPerObjectDataMap();
QMapIterator<QString, PerObjectData* > i(dataMap);
while (i.hasNext()) {
i.next();
if ( i.key() == OBJECT_BACKUPS )
backupData = i.value();
else
delete i.value();
}
dataMap.clear();
if (backupData == 0){
std::cerr << "Cannot apply backup. BackupData not found!!" << std::endl;
return;
}
// insert backup Data
dataMap.insert( OBJECT_BACKUPS, backupData);
// now insert copies of the perObjectData from the backup
for (unsigned int i=0; i < objectDatas_.size(); i++ ){
// Try to get a copy of the objectData
PerObjectData* copiedData = objectDatas_[i].second->copyPerObjectData();
if ( copiedData )
dataMap.insert( objectDatas_[i].first, copiedData );
}
}
//-----------------------------------------------------------------------------
QString BaseBackup::name(){
return name_;
}
//-----------------------------------------------------------------------------
int BaseBackup::id(){
return id_;
}
//-----------------------------------------------------------------------------
bool BaseBackup::blocked(){
return !links_.empty();
}
//-----------------------------------------------------------------------------
void BaseBackup::setLinks(IdList _objectIDs){
//remove myself from links
for(int i=_objectIDs.size()-1; i >= 0; --i )
if ( i == id_ )
_objectIDs.erase( _objectIDs.begin() + i );
//store links
links_ = _objectIDs;
}
//-----------------------------------------------------------------------------
\ No newline at end of file
/*===========================================================================*\
* *
* OpenFlipper *
* Copyright (C) 2001-2011 by Computer Graphics Group, RWTH Aachen *
* www.openflipper.org *
* *
*--------------------------------------------------------------------------- *
* This file is part of OpenFlipper. *
* *
* OpenFlipper is free software: you can redistribute it and/or modify *
* it under the terms of the GNU Lesser General Public License as *
* published by the Free Software Foundation, either version 3 of *
* the License, or (at your option) any later version with the *
* following exceptions: *
* *
* If other files instantiate templates or use macros *
* or inline functions from this file, or you compile this file and *
* link it with other files to produce an executable, this file does *
* not by itself cause the resulting executable to be covered by the *
* GNU Lesser General Public License. This exception does not however *
* invalidate any other reasons why the executable file might be *
* covered by the GNU Lesser General Public License. *
* *
* OpenFlipper 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 Lesser General Public License for more details. *
* *
* You should have received a copy of the GNU LesserGeneral Public *
* License along with OpenFlipper. If not, *
* see <http://www.gnu.org/licenses/>. *
* *
\*===========================================================================*/
/*===========================================================================*\
* *
* $Revision: 10745 $ *
* $LastChangedBy: moebius $ *
* $Date: 2011-01-26 10:23:50 +0100 (Wed, 26 Jan 2011) $ *
* *
\*===========================================================================*/
#ifndef BASEBACKUP_HH
#define BASEBACKUP_HH
#include <QString>
#include <OpenFlipper/common/BaseObjectData.hh>
#include <OpenFlipper/common/UpdateType.hh>
#include <OpenFlipper/common/perObjectData.hh>
/**
* @brief Class that encapsulates a backup
*/
class BaseBackup
{
public:
BaseBackup(QString _name);
BaseBackup(BaseObjectData* _object, QString _name, UpdateType _type);
virtual ~BaseBackup();
public:
virtual void apply();
QString name();
void setLinks(IdList _objectIDs);
int id();
bool blocked();
protected:
//backup of the perObjectData objects
std::vector< std::pair<QString, PerObjectData*> > objectDatas_;
BaseObjectData* object_;
QString name_;
IdList links_;
int id_;
};
#endif //BASEBACKUP_HH
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