/*****************************************************************************
 * $LastChangedDate: 2011-04-23 21:07:07 -0400 (Sat, 23 Apr 2011) $
 * @file
 * @author  Jim E. Brooks  http://www.palomino3d.org
 * @brief   Periodically destroys zombie Objects.
 *//*
 * LEGAL:   COPYRIGHT (C) 2008 JIM E. BROOKS
 *          THIS SOURCE CODE IS RELEASED UNDER THE TERMS
 *          OF THE GNU GENERAL PUBLIC LICENSE VERSION 2 (GPL 2).
 *****************************************************************************/

#ifndef OBJECT_ZOMBIES_HH
#define OBJECT_ZOMBIES_HH 1

#define GET_ZOMBIE_OBJECTS() (ZombieObjects::GetInstance())

#include <vector>
#include "base/singleton.hh"
#include "base/timer.hh"

#if DEBUG
namespace program { class Program; }
#endif

namespace object {

////////////////////////////////////////////////////////////////////////////////
/// @brief Periodically destroys zombie Objects.
///
/// Rationale:
/// Object::Zombify() is the catalyst for broadcasting the DestroyObject event.
/// Yet, it cannot be broadcast while executing Object::Zombify() because
/// of premature deletation (what if its refCount reaches zero!).
/// So, Object::Zombify() delays its destruction by enqueueing itself into
/// this container which is pulsed by a timer-tick for a safe-time to delete zombies.
///
class ZombieObjects
{
friend class Object;  // only for Object::Zombify()
#if DEBUG
friend class program::Program;
#endif

private:
            ZombieObjects( void );
            ~ZombieObjects();
            DEFINE_GetInstance( ZombieObjects )  // Singleton
    void    Zombify( shptr<Object> zombie );
    void    Tick( void );
    void    DestroyZombies( void ) { Tick(); }

private:
    /// @brief Timer-tick.
    CLASS_TICK_FUNCTOR_BASIC

private:
    DECLARE_SINGLETON_CLASS_VARS( ZombieObjects )
    std::vector<shptr<Object> > mZombies;
    shptr<TickFunctor>          mTickFunctor;
};

} // namespace object

#endif // OBJECT_ZOMBIES_HH
