Add the ability to flash a gwin window/widget.

Only the button draws for checkbox's and radio's currently do anything about it.
Widget demo updated to show this on Checkbox 3 (the toggle button).
ugfx_release_2.6
inmarket 2015-01-25 17:40:34 +10:00
parent b316263833
commit b9f53aa793
9 changed files with 180 additions and 2 deletions

View File

@ -51,6 +51,7 @@
#define GFX_USE_GWIN TRUE
#define GWIN_NEED_WINDOWMANAGER TRUE
#define GWIN_NEED_FLASHING TRUE
#define GWIN_NEED_CONSOLE TRUE
#define GWIN_CONSOLE_USE_HISTORY TRUE

View File

@ -79,6 +79,8 @@ static const GWidgetStyle YellowWidgetStyle = {
static font_t font;
static GListener gl;
static GHandle ghConsole;
static GTimer FlashTimer;
#if GWIN_NEED_TABSET
static GHandle ghTabset;
#else
@ -485,6 +487,12 @@ static void setEnabled(bool_t ena) {
//gwinSetEnabled(ghCheckDisableAll, TRUE);
}
static void FlashOffFn(void *param) {
(void) param;
gwinNoFlash(ghCheckbox3);
}
int main(void) {
GEvent * pe;
@ -517,6 +525,7 @@ int main(void) {
// We want to listen for widget events
geventListenerInit(&gl);
gwinAttachListener(&gl);
gtimerInit(&FlashTimer);
#if !GWIN_NEED_TABSET
// Press the Tab we want visible
@ -543,6 +552,11 @@ int main(void) {
if (((GEventGWinCheckbox *)pe)->gwin == ghCheckDisableAll) {
gwinPrintf(ghConsole, "%s All\n", ((GEventGWinCheckbox *)pe)->isChecked ? "Disable" : "Enable");
setEnabled(!((GEventGWinCheckbox *)pe)->isChecked);
// If it is the toggle button checkbox start the flash.
} else if (((GEventGWinCheckbox *)pe)->gwin == ghCheckbox3) {
gwinFlash(ghCheckbox3);
gtimerStart(&FlashTimer, FlashOffFn, 0, FALSE, 3000);
}
break;

View File

@ -148,6 +148,8 @@
//#define GWIN_NEED_WINDOWMANAGER FALSE
// #define GWIN_REDRAW_IMMEDIATE FALSE
// #define GWIN_REDRAW_SINGLEOP FALSE
// #define GWIN_NEED_FLASHING FALSE
// #define GWIN_FLASHING_PERIOD 250
//#define GWIN_NEED_CONSOLE FALSE
// #define GWIN_CONSOLE_USE_HISTORY FALSE

View File

@ -547,6 +547,40 @@ extern "C" {
*/
GHandle gwinGetNextWindow(GHandle gh);
/**
* @brief Set a window or widget to flash
*
* @param[in] gh The window handle
* @param[in] flash Enable or disable the flashing of the window
*
* @note The window is automatically redrawn if it supports self-redrawing.
* @note When a window is set to flash, its appearance changes in some
* way every flash period (GWIN_FLASHING_PERIOD). How its appearance
* changes depends on the draw for each window/widget.
*
* @pre Requires GWIN_NEED_FLASHING to be TRUE
*
* @api
*/
void gwinSetFlashing(GHandle gh, bool_t flash);
/**
* @brief Enables flashing of a window or widget
*
* @param[in] gh The window handle
*
* @api
*/
#define gwinFlash(gh) gwinSetFlashing(gh, TRUE)
/**
* @brief Disables a widget
*
* @param[in] gh The window handle
*
* @api
*/
#define gwinNoFlash(gh) gwinSetFlashing(gh, FALSE)
#endif
#if GDISP_NEED_TEXT || defined(__DOXYGEN__)

View File

@ -216,6 +216,11 @@ void gwinCheckboxDraw_CheckOnRight(GWidgetObject *gw, void *param) {
if (gw->g.vmt != (gwinVMT *)&checkboxVMT) return;
pcol = getDrawColors(gw);
#if GWIN_NEED_FLASHING
// Flash the on and off state.
pcol = _gwinGetFlashedColor(gw, pcol, TRUE);
#endif
gdispGFillStringBox(gw->g.display, gw->g.x, gw->g.y, gw->g.width-1, gw->g.height-1, gw->text, gw->g.font, pcol->text, pcol->fill, justifyCenter);
gdispGDrawLine(gw->g.display, gw->g.x+gw->g.width-1, gw->g.y, gw->g.x+gw->g.width-1, gw->g.y+gw->g.height-1, pcol->edge);
gdispGDrawLine(gw->g.display, gw->g.x, gw->g.y+gw->g.height-1, gw->g.x+gw->g.width-2, gw->g.y+gw->g.height-1, pcol->edge);
@ -232,6 +237,11 @@ void gwinCheckboxDraw_CheckOnRight(GWidgetObject *gw, void *param) {
if (gw->g.vmt != (gwinVMT *)&checkboxVMT) return;
pcol = getDrawColors(gw);
#if GWIN_NEED_FLASHING
// Flash the on and off state.
pcol = _gwinGetFlashedColor(gw, pcol, TRUE);
#endif
/* Fill the box blended from variants of the fill color */
tcol = gdispBlendColor(White, pcol->fill, TOP_FADE);
bcol = gdispBlendColor(Black, pcol->fill, BOTTOM_FADE);

View File

@ -47,6 +47,7 @@
#define GWIN_FLG_MINIMIZED 0x00100000 // @< The window is minimized
#define GWIN_FLG_MAXIMIZED 0x00200000 // @< The window is maximized
#define GWIN_FLG_MOUSECAPTURE 0x00400000 // @< The window has captured the mouse
#define GWIN_FLG_FLASHING 0x00800000 // @< The window is flashing - see the _gwinFlashState boolean
#define GWIN_FIRST_WM_FLAG 0x01000000 // @< 8 bits free for the window manager to use
#define GWIN_LAST_WM_FLAG 0x80000000 // @< 8 bits free for the window manager to use
/** @} */
@ -165,7 +166,9 @@ typedef struct gwinVMT {
/**
* @brief The current window manager
*/
extern GWindowManager * _GWINwm;
extern GWindowManager * _GWINwm;
extern bool_t _gwinFlashState;
#endif
#ifdef __cplusplus
@ -313,6 +316,20 @@ bool_t _gwinWMAdd(GHandle gh, const GWindowInit *pInit);
* @notapi
*/
void _gwinSendEvent(GHandle gh, GEventType type);
#if GWIN_NEED_FLASHING || defined(__DOXYGEN__)
/**
* @brief Convert a chosen style color set pressed/enabled etc if flashing
* @return The colorset - after flashing is taken into account
*
* @param[in] gw The widget
* @param[in] pcol The style color set that has been chosen to reflect the state of the widget
* @param[in] flashOffState Whether the off-state should be flashed as well. If false, only the
* pressed color set is flashed.
*/
const GColorSet *_gwinGetFlashedColor(GWidgetObject *gw, const GColorSet *pcol, bool_t flashOffState);
#endif
#endif
#if GWIN_NEED_CONTAINERS || defined(__DOXYGEN__)

View File

@ -328,6 +328,21 @@
#ifndef GWIN_TABSET_TABHEIGHT
#define GWIN_TABSET_TABHEIGHT 18
#endif
/**
* @brief Should flashing of widgets be supported
* @details Defaults to FALSE
* @pre Requires GWIN_NEED_WINDOWMANAGER to be TRUE
*/
#ifndef GWIN_NEED_FLASHING
#define GWIN_NEED_FLASHING FALSE
#endif
/**
* @brief What is the period for the flashing timer
* @details Defaults to 250 milliseconds
*/
#ifndef GWIN_FLASHING_PERIOD
#define GWIN_FLASHING_PERIOD 250
#endif
/** @} */
#endif /* _GWIN_OPTIONS_H */

View File

@ -203,7 +203,12 @@ void gwinRadioDraw_Radio(GWidgetObject *gw, void *param) {
if (gw->g.vmt != (gwinVMT *)&radioVMT) return;
pcol = getDrawColors(gw);
#if GWIN_NEED_FLASHING
// Flash only the on state.
pcol = _gwinGetFlashedColor(gw, pcol, FALSE);
#endif
gdispGFillStringBox(gw->g.display, gw->g.x, gw->g.y, gw->g.width-1, gw->g.height-1, gw->text, gw->g.font, pcol->text, pcol->fill, justifyCenter);
gdispGDrawLine(gw->g.display, gw->g.x+gw->g.width-1, gw->g.y, gw->g.x+gw->g.width-1, gw->g.y+gw->g.height-1, pcol->edge);
gdispGDrawLine(gw->g.display, gw->g.x, gw->g.y+gw->g.height-1, gw->g.x+gw->g.width-2, gw->g.y+gw->g.height-1, pcol->edge);
@ -215,6 +220,11 @@ void gwinRadioDraw_Radio(GWidgetObject *gw, void *param) {
if (gw->g.vmt != (gwinVMT *)&radioVMT) return;
pcol = getDrawColors(gw);
#if GWIN_NEED_FLASHING
// Flash only the on state.
pcol = _gwinGetFlashedColor(gw, pcol, FALSE);
#endif
if ((gw->g.flags & GRADIO_FLG_PRESSED)) {
gdispGDrawBox(gw->g.display, gw->g.x, gw->g.y, gw->g.width, gw->g.height, pcol->edge);
gdispGFillStringBox(gw->g.display, gw->g.x+1, gw->g.y+1, gw->g.width-2, gw->g.height-1, gw->text, gw->g.font, pcol->text, pcol->fill, justifyCenter);

View File

@ -161,9 +161,13 @@
// The default window manager
extern const GWindowManager GNullWindowManager;
GWindowManager * _GWINwm;
bool_t _gwinFlashState;
static gfxSem gwinsem;
static gfxQueueASync _GWINList;
#if GWIN_NEED_FLASHING
static GTimer FlashTimer;
#endif
#if !GWIN_REDRAW_IMMEDIATE
static GTimer RedrawTimer;
static void RedrawTimerFn(void *param);
@ -171,6 +175,7 @@ static gfxQueueASync _GWINList;
static volatile uint8_t RedrawPending;
#define DOREDRAW_INVISIBLES 0x01
#define DOREDRAW_VISIBLES 0x02
#define DOREDRAW_FLASHRUNNING 0x04
/*-----------------------------------------------
@ -181,6 +186,9 @@ void _gwmInit(void)
{
gfxSemInit(&gwinsem, 1, 1);
gfxQueueASyncInit(&_GWINList);
#if GWIN_NEED_FLASHING
gtimerInit(&FlashTimer);
#endif
#if !GWIN_REDRAW_IMMEDIATE
gtimerInit(&RedrawTimer);
gtimerStart(&RedrawTimer, RedrawTimerFn, 0, TRUE, TIME_INFINITE);
@ -563,6 +571,73 @@ GHandle gwinGetNextWindow(GHandle gh) {
return gh ? (GHandle)gfxQueueASyncNext(&gh->wmq) : (GHandle)gfxQueueASyncPeek(&_GWINList);
}
#if GWIN_NEED_FLASHING
static void FlashTimerFn(void *param) {
GHandle gh;
(void) param;
// Assume we will be stopping
RedrawPending &= ~DOREDRAW_FLASHRUNNING;
// Swap the flash state
_gwinFlashState = !_gwinFlashState;
// Redraw all flashing windows
for(gh = (GHandle)gfxQueueASyncPeek(&_GWINList); gh; gh = (GHandle)gfxQueueASyncNext(&gh->wmq)) {
if ((gh->flags & GWIN_FLG_FLASHING)) {
RedrawPending |= DOREDRAW_FLASHRUNNING;
_gwinUpdate(gh);
}
}
// Do we have no flashers left?
if (!(RedrawPending & DOREDRAW_FLASHRUNNING))
gtimerStop(&FlashTimer);
}
void gwinSetFlashing(GHandle gh, bool_t flash) {
// Start flashing?
if (flash) {
gh->flags |= GWIN_FLG_FLASHING; // A redraw will occur on the next flash period.
// Start the flash timer if needed
if (!(RedrawPending & DOREDRAW_FLASHRUNNING)) {
RedrawPending |= DOREDRAW_FLASHRUNNING;
// Ensure we start the timer with flash bit on
_gwinFlashState = FALSE;
FlashTimerFn(0); // First flash
gtimerStart(&FlashTimer, FlashTimerFn, 0, TRUE, GWIN_FLASHING_PERIOD); // Subsequent flashes
}
// Stop flashing?
} else if ((gh->flags & GWIN_FLG_FLASHING)) {
gh->flags &= ~GWIN_FLG_FLASHING;
// We need to manually redraw as the timer is now turned off for this window
_gwinUpdate(gh);
}
}
#if GWIN_NEED_WIDGET
const GColorSet *_gwinGetFlashedColor(GWidgetObject *gw, const GColorSet *pcol, bool_t flashOffState) {
// Does the flashing state affect the current colors?
if ((gw->g.flags & GWIN_FLG_FLASHING) && _gwinFlashState) {
// For a pressed state show an unpressed state
if (pcol == &gw->pstyle->pressed)
pcol = &gw->pstyle->enabled;
// For a non-pressed state (if allowed) show a pressed state
else if (flashOffState && pcol == &gw->pstyle->enabled)
pcol = &gw->pstyle->pressed;
}
return pcol;
}
#endif
#endif
/*-----------------------------------------------
* "Null" Window Manager Routines
*-----------------------------------------------*/