
/***************************************************************************
 *                                                                         *
 *   KCPULoad and KNetLoad are copyright (c) 1999-2000, Markus Gustavsson  *
 *                                       (c) 2002, Ben Burton              *
 *                                                                         *
 *   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; either version 2 of the License, or     *
 *   (at your option) any later version.                                   *
 *                                                                         *
 ***************************************************************************/

#ifndef __STATPOPUP_H
#define __STATPOPUP_H

#include <tqwidget.h>
#include <vector>   // sorry, TQValueVector::erase() does not call destructors

class TDEAction;
class TDEActionCollection;
class TDEConfig;
class TDEPopupMenu;
class TDERadioAction;
class TDESelectAction;
class TDEToggleAction;
class TQTimer;
class StatDock;

/**
 * A small pop-up window that contains a continually updating display of
 * statistics.
 *
 * This pop-up will be sticky and stay-on-top by default.
 *
 * Up to two windows docked in the system tray (of class StatDock) can
 * be maintained by this pop-up.  There should only be one StatPopup
 * per application.
 *
 * Note that initDock() \e must be called when a system tray window is
 * created, though it is generally called automatically from the StatDock
 * constructor.
 *
 * Note also that the constructor for this class does \e not call
 * setupActions(), readPopupState() or startUpdates(); these must all be
 * called by other routines (such as subclass constructors), since they
 * require either subclass initialisation or an existing system tray
 * window.
 */
class StatPopup : public TQWidget {
    TQ_OBJECT
  

public:
    /**
     * Colour constants.
     */
    static const TQColor colorBorder;

public:
    /**
     * Constructors and destructors.
     *
     * This constructor will set the config variable but will not read
     * any configuration information.  See the general class notes also
     * for a list of other routines this constructor will not call.
     */
    StatPopup(bool useSupportSplit, TQWidget *parent = 0, const char *name = 0);
    ~StatPopup();

    /**
     * Geometric pop-up state management.
     */
    void readPopupState();
    void savePopupState();

    /**
     * Initialises the given system tray window and its context menu.
     *
     * All global application properties (i.e., properties held by this
     * pop-up) will be propagated to the system tray window, and all
     * global application actions will be added to the given menu.
     *
     * Parameter whichDock must be either 0 or 1 to specify whether the
     * given system tray window will become window dock[0] or dock[1].
     *
     * This routine \e must be called when a system tray window is first
     * created, though in general this will be done automatically by the
     * StatDock constructor.
     */
    virtual void initDock(StatDock* target, TDEPopupMenu* menu, int whichDock);

    /**
     * Is this application currently active (i.e., taking periodic
     * readings and displaying them)?
     */
    bool isActive() const;

    /**
     * Are split diagrams currently enabled?
     */
    bool isSplit() const;

    /**
     * Returns the frequency of updates in milliseconds.
     */
    int getSpeed() const;

public slots:
    /**
     * Slots for menu items.
     */
    void setActive(bool);
    void clearHistory();
    void selectSpeed();
    void setSplit(bool);
    void setFillLines();
    void setFillBars();
    void setFillShaded();
    void setSoft(bool);
    void setLabelled(bool);
    void setGrid(bool);
    void selectColor();

protected:
    /**
     * Return a human-readable name and default diagram colour for each
     * system tray window.
     * The argument given will be either 0 or 1, referring to window
     * dock[0] or dock[1] respectively.
     */
    virtual TQString dockName(int which) const = 0;
    virtual TQColor defaultDockColor(int which) const = 0;

    /**
     * Take a fresh reading.  Subclasses must override this routine.
     *
     * This routine must update the array upper.
     * If split readings are enabled, it must also update the array lower.
     * If this pop-up is visible, it must also update the string fullReading.
     */
    virtual void takeReadingInternal() = 0;

    /**
     * Sets up any actions specific to subclasses of StatPopup.
     * The global configuration should be read at this point to set the
     * initial states of these actions.
     *
     * This routine will be called during setupActions().
     */
    virtual void setupCustomActions() {}

    /**
     * Inserts any menu items specific to subclasses of StatPopup into
     * the given menu.  If any items are inserted, a separator should
     * be inserted after them.
     *
     * This routine will be called during initDock().
     */
    virtual void insertCustomItems(TDEPopupMenu*) {}

    /**
     * Propagates any properties specific to subclasses of StatPopup to
     * the given system tray window during its initialisation.
     *
     * This routine will be called during initDock().
     */
    virtual void setCustomProperties(StatDock*) {}

    /**
     * Returns the first non-null pointer out of dock[0] and dock[1], or
     * returns null if both these pointers are null.
     */
    StatDock* firstDock();

    /**
     * Start and stop the periodic taking of readings.
     */
    void startUpdates();
    void stopUpdates();

    /**
     * Set up the collection of appliation-wide actions.
     * The global configuration will be read at this point to set the
     * initial states of these actions.
     */
    virtual void setupActions();

    /**
     * Request that this pop-up be resized at the next reading according
     * to its text contents.  The pop-up will be resized \e after the
     * reading is taken.
     */
    void requestResize();

    /**
     * Custom painting routine.
     */
    void paintEvent(TQPaintEvent *);

    /**
     * Overrides for dragging support.
     */
    void mousePressEvent(TQMouseEvent *);
    void mouseReleaseEvent(TQMouseEvent *);
    void mouseMoveEvent(TQMouseEvent *);

    /**
     * Overrides for saving the popup state.
     */
    void closeEvent(TQCloseEvent *);
    void hideEvent(TQHideEvent *);
    void showEvent(TQShowEvent *);

protected slots:
    /**
     * Take a fresh reading and update all visual elements accordingly.
     */
    void takeReading();

protected:
    /**
     * Configuration and GUI elements.
     */
    TDEConfig* config;
        /**< The configuration for the underlying application. */

    /**
     * Contains the readings per CPU.
     */
    struct Reading {
        StatDock* dock;
            /**< The system tray window maintained by this pop-up.
                 May be null. */
        int upper;
            /**< The upper reading taken during the last reading. */
        int lower;
            /**< The lower reading taken during the last reading. */
        TQColor color;
            /**< The colour used in the system tray diagram. */
        TDEAction* actColor;
            /**< The menu item to change the colour of this dock. */
        Reading();
        ~Reading();
        void Init(int which, StatPopup* popup);
    };
    std::vector<Reading> r;
        /**< The readings maintained by this pop-up. */
    TDEActionCollection* coll;
        /**< The collection of all application-level actions. */

    TQString fullReading;
        /**< A full string describing the last reading taken,
             to be displayed in this pop-up. */

private:
    /**
     * Resize this pop-up according to its text contents (i.e., the
     * variable fullReading).  A little extra room will be added to
     * accomodate potential minor variations in the text.
     */
    void resizeToText();

private:
    /**
     * Update support.
     */
    TQTimer* timer;
        /**< The timer handling periodic updates. */
    int speed;
        /**< The frequency of updates in milliseconds. */

    /*
     * Diagram support.
     */
    int fillStyle;
        /**< The fill style used in the system tray diagrams. */
    bool supportSplit;
        /**< Does this application support split diagrams? */

    /**
     * Pop-up support.
     */
    int relX;
        /**< The X coordinate of this pop-up at the beginning of a drag
             operation. */
    int relY;
        /**< The Y coordinate of this pop-up at the beginning of a drag
             operation. */
    bool isDragged;
        /**< Are we in the middle of a drag operation? */
    bool closing;
        /**< Have we received a close event? */
    bool resizeRequested;
        /**< Has a pop-up resize been requested? */

    /**
     * Actions
     */
    TDEToggleAction* actActive;
    TDEAction* actClearHistory;
    TDEAction* actSpeed;
    TDEToggleAction* actSplit;
    TDEToggleAction* actFillLines;
    TDEToggleAction* actFillBars;
    TDEToggleAction* actFillShaded;
    TDEToggleAction* actSoft;
    TDEToggleAction* actLabelled;
    TDEToggleAction* actGrid;
};

inline int StatPopup::getSpeed() const {
    return speed;
}

inline void StatPopup::requestResize() {
    resizeRequested = true;
}

#endif
