/*
 * Author: Andrew Mann
 *
 * Copyright (C) 2004 PlaneShift Team (info@planeshift.it,
 * http://www.planeshift.it)
 *
 * This program 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 (version 2 of the License)
 * This program 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 this program; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
 *
 */

#ifndef __PARTVIEW_DOT_H__
#define __PARTVIEW_DOT_H__

#include <stdarg.h>
#include "csutil/ref.h"
#include "imesh/object.h"
#include "iengine/mesh.h"
#include "pv_helpers.h"

struct iEngine;
struct iLoader;
struct iGraphics3D;
struct iKeyboardDriver;
struct iVirtualClock;
struct iObjectRegistry;
struct iEvent;
struct iSector;
struct iView;
struct iHeightGridFactory;
struct iImageIO;
struct iMeshWrapper;
struct iPluginManager;
struct iLoaderPlugin;
class pawsMainWidget;
class guiMenuBar;
class guiPSList;
class guiMaterialList;
class DirectionArrow;
class PVResourceManager;


class PartSystemTracker
{
public:
    PartSystemTracker(csRef<iMeshWrapper> psystem_wrapper,const char *pname,csRef<iMeshFactoryWrapper> psfactory);
    ~PartSystemTracker();

    void ShowOrientationArrows(bool show);
    bool OrientationArrowsVisible();


    csRef<iMeshWrapper> particle_system_wrapper;
    csRef<iMeshFactoryWrapper> ps_factory_wrapper;
    csString name;
    CoordinateArrows *orientation_arrows;
    bool system_stopping;

private:
    bool show_arrows;
};


class PartViewApp
{
public:
  static PartViewApp *g_pApp;

public:
  PartViewApp(iObjectRegistry* object_reg);
  ~PartViewApp();


  // Convert a click in screen coordinates to a world coordinate vector and position
  void ScreenToWorld(int x, int y,csVector3 &unit_zpos,csVector3 &clickpos);

  /// Initialization function
  bool Initialize();
  /// Main runloop
  void Run();

  /// Static event handler callback
  static bool StaticEventHandler(iEvent &ev);

  // Retrieve the pointer to the resource manager
  PVResourceManager *GetResourceManager() { return resource_manager; }

  PartSystemTracker *NewParticleSystem(const char *system_name,csVector3 position);
  PartSystemTracker *NewParticleSystemAtCamera(const char *system_name);
  void RemoveParticleSystem(PartSystemTracker *ps_track);

  bool LoadParticleSystem(const char *filename);
  bool SaveParticleSystem(PartSystemTracker *ps_track, const char *filename);


  void PointFromCenterOfCamera(float distance,csVector3 &world_point);


  // Let the application specific GUI modify our private parameters
//  friend class pawsHM_TopLevel;

protected:
  bool RegisterPawsFactories();
  bool LoadPawsWidgets();
  bool TryLoadPawsWidget(const char *xml_filename);

  void TimedProcessing(csTicks elapsed);
  bool CreateDefaultRoom();
  bool LoadMapFileAsRoom(const char *mapfile);



public:
  // The object registry interface.  This is a list of interfaces based on their text name
  iObjectRegistry* object_reg;
protected:
  // The virtual clock interface, we control how often this is updated
  csRef<iVirtualClock> vc;
  // The Crystal Space engine interface
  csRef<iEngine> engine;
  // The 3d renderer interface
  csRef<iGraphics3D> g3d;
  // The 2d display interface - used for the PAWS UI system
  csRef<iGraphics2D> g2d;
  // The keyboard input driver interface
  csRef<iKeyboardDriver> kbd;
  // The Crystal Space "Loader".  This plugin handles parsing all kinds of data into CS usable objects.
  csRef<iLoader> loader;
  // The Virtual File System Interface.
  csRef<iVFS> vfs;
  // The plugin manager
  csRef<iPluginManager> plgmgr;
  // Loader for "particles" particle system plugin
  csRef<iLoaderPlugin> particlesloader;

  // The interface to the current view parameters
  csRef<iView> view;

  // Pointer to a paws window manager
  PawsManager *paws;
  // The top level widget for the paws interface
  pawsMainWidget* mainWidget;
  // The menu bar pawsWidget - always up, only one
  guiMenuBar *menubar;
  // The material list view - not always visible, only one
  guiMaterialList *matlistgui;
  // The left particle system frame
  guiPSList *pslistgui;


  // Pointer to the resource manager
  PVResourceManager *resource_manager;





  /// The PAWS widget that has the main menu and most of the gui related logic
//  pawsHM_TopLevel *gui_menu_widget;

  // The window for loading and saving.  Check gui_save_outstanding or gui_load_outstanding
  // to determine wether this window is visible and if it's being used for a load or save.
//  pawsFileNavigation *load_save_widget;

  //
  // A sector in CS is a logical region of space where meshes, lights, etc are placed.
  //  Sectors are joined by portals.  We have a single sector for now.
  iSector *the_room;

  // Current rotation of the view
  float rotX, rotY;


  // Bool indicating wether the left mouse button is currently up or down
  bool mouse_left_down,mouse_right_down;
  unsigned int last_int_x,last_int_z;
  int last_mouseright_y;




  // A value to track wether our window is visible or not so we can decide wether to spend time drawing to the screen
  bool window_visible;


  bool EventHandler(iEvent &ev);

  void StartFrame ();
  void FinishFrame ();


  friend class guiMenuBar;
  friend class guiMaterialList;
};


#endif // __PARTVIEW_DOT_H__

