/***************************************************************************
 *   Copyright (C) 2004 - 2005 by Raphael Langerhorst                      *
 *   raphael-langerhorst@gmx.at                                            *
 *                                                                         *
 *   Permission is hereby granted, free of charge, to any person obtaining *
 *   a copy of this software and associated documentation files (the       *
 *   "Software"), to deal in the Software without restriction, including   *
 *   without limitation the rights to use, copy, modify, merge, publish,   *
 *   distribute, sublicense, and/or sell copies of the Software, and to    *
 *   permit persons to whom the Software is furnished to do so, subject to *
 *   the following conditions:                                             *
 *                                                                         *
 *   The above copyright notice and this permission notice shall be        *
 *   included in all copies or substantial portions of the Software.       *
 *                                                                         *
 *   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,       *
 *   EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF    *
 *   MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.*
 *   IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR     *
 *   OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, *
 *   ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR *
 *   OTHER DEALINGS IN THE SOFTWARE.                                       *
 ***************************************************************************/


#ifndef GWEINTERFACESIMPLEH
#define GWEINTERFACESIMPLEH


#include <GweController.h>
#include <GDataController.h>

#include <GMatrix44.h>

#include <qptrlist.h>
#include <qmutex.h>


namespace GWE
{

class GweSimpleDataController : public GDataController
{
  Q_OBJECT
  private:
  
    /**
     * Represents the whole storage mechanism for this "simple"
     * GWE.
     * @todo use some hash table for this (GElementID as identifier)...
     */
    QPtrList<GCS::GElement> Elements;
    
    /**
     * Used for locking the elements list.
     * This is important for threaded access.
     */
    QMutex* ElementListMutex;
    
  protected:
    
    /**
     * Searches for the element with given ID and returns it.
     * If the element does not exist, NULL is returned.
     */
    GCS::GElement* getElement(const GCS::GElementID& id) const;
  
  public:
  
    /**
     * Constructor.
     */
    GweSimpleDataController();
  
    /**
     * Virtual destructor
     */
    virtual ~GweSimpleDataController();
    
    // GDataController implementation //
    
    virtual const GCS::GElement* read(const GCS::GElementID&) const;
    
    virtual QValueList<GCS::GElementID> getChildren(const GCS::GElementID& parent) const;
    
    virtual GCS::GElement* open(const GCS::GElementID&);
    
    virtual GCS::GElement* getOpenElement(const GCS::GElementID& );

    virtual const QValueList<GCS::GElementID> getListOfOpenElements();

    virtual const QValueList<GCS::GElementID> getListOfAllElements();
    
  public slots:
    
    virtual bool add(GCS::GElement* );
    
    virtual bool writeOpenElementToStorage(const GCS::GElementID& );
    
    virtual bool close(const GCS::GElementID& );
    
    virtual bool postDelete(const GCS::GElementID& );

    virtual void shutdown();

};


/**
  \class GweSimpleController GweSimpleController.h
  \brief Provides local non-persistent GWE functionality
  @author Raphael Langerhorst
  
  GweSimpleController implements both the GweController and
  the GDataController interface,
  all functionality provided in this class works as stated
  in the documentation of these classes;
  
  the only exception is that data can't be kept persistent -
  all elements are only held in application memory and don't
  survive a shutdown/restart cycle.
*/

class GweSimpleController : public GweController
{
  Q_OBJECT
  
  public:
  
    /**
     * Constructor.
     */
    GweSimpleController();
  
    /**
     * Virtual destructor
     */
    virtual ~GweSimpleController();
    
  protected slots:
  
  // new element registration and element removal //
  
    /**
     * Connects all notification signals to the GWE for handling
     */
    void connectElement(const GCS::GElementID& );
  
  // note that the source of these signals are active agents;
  
    /**
     * Called when a new element is being created
     * @note used internally (protected)
     */
    virtual void newElementCreated(GCS::GElement* element);
    
    /**
     * Called when a element should be removed
     * @note used internally (protected)
     */
    virtual void elementRemoved(const GCS::GElementID& ID);
    
    /**
     * Called when an element changes its parent.
     * @note used internally (protected)
     * @note Transformation is handled by element itself,
     * this slot just exists to allow information updating.
     * In a networked GWE this might cause responsibility
     * shifting between GWE server instances.
     */
    virtual void elementReparented(GCS::GElement* element, const GCS::GElementID& oldParent, const GCS::GElementID& newParent);
    
        
  public slots:
        
    // INFLUENCE MANAGEMENT //
  
    /**
     * @note To find all affected elements findInRange() is used.
     *
     * @see GweController::radiateInfluence(), findInRange()
     */
//     virtual void radiateInfluence(GCS::GElementInfluence& influence);
    
    /**
     * @see GweController::routeInfluence()
     */
//     virtual void routeInfluence(const GCS::GElementID& destination, GCS::GElementInfluence& influence);
};

}

#endif
