/**
 * @file  BCGraphicsDeviceDirectFB.h
 *
 * AstroNav TQTVD Header of BCGraphicsDeviceDirectFB class.
 *
 */

#ifndef BCGRAPHICSDEVICEDIRECTFB_H
#define BCGRAPHICSDEVICEDIRECTFB_H

#include <graphics/BIGraphicsDevice.h>
#include <pthread.h>
#include <graphics/IntSize.h>
#include <graphics/IntRect.h>

#include <directfb.h>


namespace BAL {

class BCGraphicsDeviceDirectFB : public BIGraphicsDevice {
public:
	BCGraphicsDeviceDirectFB();
	~BCGraphicsDeviceDirectFB();

	/**
	  *
	  */
    virtual void addUpdateListener(BIListener* listener);
    virtual void removeUpdateListener(BIListener* listener);

	/**
	  *
	  */
	virtual void initialize(uint16_t width, uint16_t height, uint8_t depth);
	/**
	  *
	  */
	virtual void finalize();
	/**
	  *
	  */
	virtual BINativeImage* createNativeImage(const WebCore::IntSize size);
	virtual BINativeImage* createNativeImage(RGBA32Array&, const WebCore::IntSize size);

	/**
	  *
	  */
	virtual void copy(const BTWidget&, const BINativeImage&, WebCore::IntRect, WebCore::IntPoint, const uint8_t alphaChannel);
	/**
	  *
	  */
	virtual void drawArc(const BTWidget&, const WebCore::IntRect rect, uint16_t startAngle, uint16_t angleSpan, const WebCore::Color);
	/**
	  *
	  */
	virtual void drawEllipse(const BTWidget&, WebCore::IntRect, const WebCore::Color);
	/**
	  *
	  */
	virtual void drawLine(const BTWidget&, WebCore::IntPoint, WebCore::IntPoint, const WebCore::Color);
	/**
	  *
	  */
	virtual void drawRect(const BTWidget&, WebCore::IntRect, const WebCore::Color);
	/**
	  *
	  */
	virtual void fillConvexPolygon(const BTWidget&, size_t numPoints, const WebCore::IntPoint*, const WebCore::Color);
	/**
	  *
	  */
	virtual void fillRect(const BTWidget&, WebCore::IntRect, const WebCore::Color);
	/**
	  *
	  */
	virtual void setClip(const BTWidget&, WebCore::IntRect);
	/**
	  *
	  */
	virtual WebCore::IntRect clip(const BTWidget&);
	/**
	  *
	  */
	virtual void stretchBlit(const BTWidget&, const BINativeImage&, WebCore::IntRect src, WebCore::IntRect dst, const uint8_t alphaChannel);
	virtual WebCore::IntSize size() const;
	virtual void update(const BTWidget&, const WebCore::IntRect);
	virtual void clear(const BTWidget&, const WebCore::IntRect);
public:
	void *	setSuperInterface	 (void* dfb);
	void *	getSuperInterface	 (void) { return (void *) m_directfb; }
	void *	setPrimarySurface (void* ps);
	void *	getPrimarySurface (void) { return (void *) m_screen; }

	void setScreenLessMode(bool mode);

	void             setBackgroundColor(WebCore::RGBA32 color);
	WebCore::RGBA32  getBackgroundColor(void);

private:
	inline void drawArc(const BTWidget&, const WebCore::Color, int zone, int xc, int yc, float& x0, float& y0, float x1, float y1, bool doSwap = true);
	IDirectFBSurface* applyTransparency(const BINativeImage&, const uint8_t alphaChannel);

	/* the super interface */
	IDirectFB* m_directfb;
	bool       m_ownDfb;
	
	/* the primary surface (surface of primary layer) */
	IDirectFBSurface* m_screen;
	bool              m_ownScreen;
	bool              m_screenLessMode;

	int m_width;
	int m_height;
	int m_depth;

	pthread_mutex_t  m_listenersMutex;
    BIListener*      m_listenerMap[128];
	int              m_listeners;

    WebCore::RGBA32  m_backgroundColor;

#ifndef NDEBUG
	bool             m_layoutTests;
#endif
};

} // namespace BAL

#endif // BCGRAPHICSDEVICEDIRECTFB_H
