apps/examples/pwfb: Extend example to verify software cursors. Untested on initial commit.
This commit is contained in:
parent
0ff0a97ae4
commit
99382df286
@ -35,7 +35,10 @@
|
||||
|
||||
-include $(TOPDIR)/Make.defs
|
||||
|
||||
# NuttX NX Graphics Example.
|
||||
# NuttX per-window frame buffer graphics example.
|
||||
|
||||
NXGLYPHS = $(APPDIR)$(DELIM)graphics$(DELIM)nxglyphs
|
||||
CFLAGS += ${shell $(INCDIR) $(INCDIROPT) "$(CC)" "$(NXGLYPHS)$(DELIM)include"}
|
||||
|
||||
ASRCS =
|
||||
CSRCS = pwfb_events.c pwfb_motion.c
|
||||
@ -44,7 +47,7 @@ MAINSRC = pwfb_main.c
|
||||
CONFIG_EXAMPLES_PWFB_PROGNAME ?= pwfb$(EXEEXT)
|
||||
PROGNAME = $(CONFIG_EXAMPLES_PWFB_PROGNAME)
|
||||
|
||||
# NX built-in application info
|
||||
# Per-Window frame buffer built-in application info
|
||||
|
||||
CONFIG_EXAMPLES_PWFB_CLIENT_PRIO ?= SCHED_PRIORITY_DEFAULT
|
||||
CONFIG_EXAMPLES_PWFB_CLIENT_STACKSIZE ?= 2048
|
||||
|
@ -148,6 +148,20 @@
|
||||
# endif
|
||||
#endif
|
||||
|
||||
/* Cursor timing */
|
||||
|
||||
#if CONFIG_EXAMPLES_PWFB_RATECONTROL > 0
|
||||
# define CURSOR_MOVING_DELAY (3000 / CONFIG_EXAMPLES_PWFB_RATECONTROL)
|
||||
# define CURSOR_STATIONARY_DELAY (2000 / CONFIG_EXAMPLES_PWFB_RATECONTROL)
|
||||
# define CURSOR_BLINKING_DELAY (5000 / CONFIG_EXAMPLES_PWFB_RATECONTROL)
|
||||
# define CURSOR_BLINK_DELAY ( 500 / CONFIG_EXAMPLES_PWFB_RATECONTROL)
|
||||
#else
|
||||
# define CURSOR_MOVING_DELAY (0)
|
||||
# define CURSOR_STATIONARY_DELAY (0)
|
||||
# define CURSOR_BLINKING_DELAY (0)
|
||||
# define CURSOR_BLINK_DELAY (0)
|
||||
#endif
|
||||
|
||||
/****************************************************************************
|
||||
* Public Types
|
||||
****************************************************************************/
|
||||
@ -167,6 +181,37 @@ struct pwfb_window_s
|
||||
b16_t deltay; /* Current Y speed */
|
||||
};
|
||||
|
||||
#ifdef CONFIG_NX_SWCURSOR
|
||||
/* We will run the cursor in 3 different states:
|
||||
*
|
||||
* 1. Moving
|
||||
* 2. Stationary
|
||||
* 3. Enabling/disabling
|
||||
*/
|
||||
|
||||
enum pfwb_cursor_state_s
|
||||
{
|
||||
PFWB_CURSOR_MOVING = 0,
|
||||
PFWB_CURSOR_STATIONARY,
|
||||
PFWB_CURSOR_BLINKING
|
||||
};
|
||||
|
||||
/* Describes the unique state of the cursor */
|
||||
|
||||
struct pwfb_cursor_s
|
||||
{
|
||||
enum pfwb_cursor_state_s state; /* Current cursor state */
|
||||
bool visible; /* True: The cursor is visible */
|
||||
int countdown; /* Countdown until next state */
|
||||
int blinktime; /* Time remaining enabled/disabled */
|
||||
b16_t xmax; /* Max X position */
|
||||
b16_t ymax; /* Max Y position */
|
||||
b16_t xpos; /* Current X position */
|
||||
b16_t ypos; /* Current Y position */
|
||||
b16_t deltax; /* Current X speed */
|
||||
b16_t deltay; /* Current Y speed */
|
||||
};
|
||||
#endif
|
||||
/* Describes the overall state of the example */
|
||||
|
||||
struct pwfb_state_s
|
||||
@ -197,6 +242,12 @@ struct pwfb_state_s
|
||||
uint8_t fwidth; /* Max width of a font in pixels */
|
||||
uint8_t spwidth; /* The width of a space */
|
||||
|
||||
#ifdef CONFIG_NX_SWCURSOR
|
||||
/* Cursor-specific state */
|
||||
|
||||
struct pwfb_cursor_s cursor;
|
||||
#endif
|
||||
|
||||
/* Window-specific state */
|
||||
|
||||
struct pwfb_window_s wndo[3];
|
||||
|
@ -62,6 +62,12 @@
|
||||
#include <nuttx/nx/nxbe.h>
|
||||
#include <nuttx/nx/nxfonts.h>
|
||||
|
||||
#ifdef CONFIG_NX_SWCURSOR
|
||||
# undef CONFIG_NXWIDGETS_BPP
|
||||
# define CONFIG_NXWIDGETS_BPP CONFIG_EXAMPLES_PWFB_BPP
|
||||
# include "cursor-arrow1-30x30.h"
|
||||
#endif
|
||||
|
||||
#include "pwfb_internal.h"
|
||||
|
||||
/****************************************************************************
|
||||
@ -492,6 +498,64 @@ errout_with_hwnd:
|
||||
return false;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: pwfb_configure_cursor
|
||||
****************************************************************************/
|
||||
|
||||
#ifdef CONFIG_NX_SWCURSOR
|
||||
static bool pwfb_configure_cursor(FAR struct pwfb_state_s *st,
|
||||
FAR struct nxgl_point_s *pos,
|
||||
double deltax, double deltay)
|
||||
{
|
||||
int ret;
|
||||
|
||||
/* Initialize the data structure */
|
||||
|
||||
st->cursor.state = PFWB_CURSOR_MOVING;
|
||||
st->cursor.countdown = CURSOR_MOVING_DELAY;
|
||||
st->cursor.blinktime = 0;
|
||||
st->cursor.xpos = pos->x;
|
||||
st->cursor.ypos = pos->y;
|
||||
st->cursor.deltax = deltax;
|
||||
st->cursor.deltay = deltay;
|
||||
|
||||
/* Set the cursor image */
|
||||
|
||||
ret = nxcursor_setimage(st->hnx, &g_arrow1Cursor);
|
||||
if (ret < 0)
|
||||
{
|
||||
printf("pwfb_configure_cursor: ERROR: "
|
||||
"nxcursor_setimage failed: %d\n",
|
||||
errno);
|
||||
return false;
|
||||
}
|
||||
|
||||
/* Set the cursor position */
|
||||
|
||||
ret = nxcursor_setposition(st->hnx, pos);
|
||||
if (ret < 0)
|
||||
{
|
||||
printf("pwfb_configure_cursor: ERROR: "
|
||||
"nxcursor_setposition failed: %d\n",
|
||||
errno);
|
||||
return false;
|
||||
}
|
||||
|
||||
/* Enable the cursor */
|
||||
|
||||
ret = nxcursor_enable(st->hnx, false);
|
||||
if (ret < 0)
|
||||
{
|
||||
printf("pwfb_configure_cursor: ERROR: "
|
||||
"nxcursor_enable failed: %d\n",
|
||||
errno);
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
#endif
|
||||
|
||||
/****************************************************************************
|
||||
* Public Functions
|
||||
****************************************************************************/
|
||||
@ -655,6 +719,20 @@ int pwfb_main(int argc, char *argv[])
|
||||
goto errout_with_hwnd3;
|
||||
}
|
||||
|
||||
#ifdef CONFIG_NX_SWCURSOR
|
||||
/* Configure the software cursor */
|
||||
|
||||
pos.x = wstate.xres / 2;
|
||||
pos.x = wstate.yres / 2;
|
||||
|
||||
if (!pwfb_configure_cursor(&wstate, &pos, 2.900, -5.253))
|
||||
{
|
||||
printf("pwfb_main: ERROR: "
|
||||
"pwfb_configure_cursor failed for window 2\n");
|
||||
goto errout_with_hwnd3;
|
||||
}
|
||||
#endif
|
||||
|
||||
/* Now loop animating the windows */
|
||||
|
||||
for (; ; )
|
||||
@ -664,12 +742,19 @@ int pwfb_main(int argc, char *argv[])
|
||||
{
|
||||
printf("pwfb_main: ERROR:"
|
||||
"pwfb_motion failed\n");
|
||||
goto errout_with_hwnd3;
|
||||
goto errout_with_cursor;
|
||||
}
|
||||
}
|
||||
|
||||
errcode = EXIT_SUCCESS;
|
||||
|
||||
errout_with_cursor:
|
||||
#ifdef CONFIG_NX_SWCURSOR
|
||||
/* Disable the cursor */
|
||||
|
||||
(void)nxcursor_enable(wstate.hnx, false);
|
||||
#endif
|
||||
|
||||
/* Close window 3 */
|
||||
|
||||
errout_with_hwnd3:
|
||||
|
@ -44,6 +44,7 @@
|
||||
#include <errno.h>
|
||||
|
||||
#include <nuttx/nx/nxglib.h>
|
||||
#include <nuttx/nx/nxcursor.h>
|
||||
#include <nuttx/nx/nxtk.h>
|
||||
|
||||
#include "pwfb_internal.h"
|
||||
@ -174,6 +175,155 @@ static inline bool pwfb_move_window(FAR struct pwfb_state_s *st, int wndx)
|
||||
return true;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: pwfb_move_cursor
|
||||
****************************************************************************/
|
||||
|
||||
#ifdef CONFIG_NX_SWCURSOR
|
||||
static inline bool pwfb_move_cursor(FAR struct pwfb_state_s *st)
|
||||
{
|
||||
FAR struct nxgl_point_s pos;
|
||||
b16_t newx;
|
||||
b16_t newy;
|
||||
int ret;
|
||||
|
||||
#ifdef CONFIG_EXAMPLES_PWFB_VERBOSE
|
||||
printf("pwfb_move_cursor: State: %u countdown: %u blinktime: %u\n",
|
||||
(unsigned int)st->cursor.state, (unsigned int)st->cursor.countdown,
|
||||
(unsigned int)st->cursor.blinktime;
|
||||
printf("pwfb_move_cursor: Velocity: (%lx.%04lx,%lx.%04lx)\n",
|
||||
(unsigned long)st->cursor.deltax >> 16,
|
||||
(unsigned long)st->cursor.deltax & 0xffff,
|
||||
(unsigned long)st->cursor.deltay >> 16,
|
||||
(unsigned long)st->cursor.deltay & 0xffff);
|
||||
#endif
|
||||
|
||||
/* Handle the update based on cursor state */
|
||||
/* If the state is not PFWB_CURSOR_STATIONARY, then update the cursor
|
||||
* position.
|
||||
*/
|
||||
|
||||
if (st->cursor.state != PFWB_CURSOR_STATIONARY)
|
||||
{
|
||||
/* Update X position */
|
||||
|
||||
newx = st->cursor.xpos + st->cursor.deltax;
|
||||
|
||||
/* Check for collision with left or right side */
|
||||
|
||||
if (newx <= 0)
|
||||
{
|
||||
newx = 0;
|
||||
st->cursor.deltax = -st->cursor.deltax;
|
||||
}
|
||||
else if (newx >= st->cursor.xmax)
|
||||
{
|
||||
newx = st->cursor.xmax;
|
||||
st->cursor.deltax = -st->cursor.deltax;
|
||||
}
|
||||
|
||||
/* Update Y position */
|
||||
|
||||
newy = st->cursor.ypos + st->cursor.deltay;
|
||||
|
||||
/* Check for collision with top or bottom side */
|
||||
|
||||
if (newy <= 0)
|
||||
{
|
||||
newy = 0;
|
||||
st->cursor.deltay = -st->cursor.deltay;
|
||||
}
|
||||
else if (newy >= st->cursor.ymax)
|
||||
{
|
||||
newy = st->cursor.ymax;
|
||||
st->cursor.deltay = -st->cursor.deltay;
|
||||
}
|
||||
|
||||
#ifdef CONFIG_EXAMPLES_PWFB_VERBOSE
|
||||
printf("pwfb_move_cursor: Old pos: (%lx.%04lx,%lx.%04lx) "
|
||||
"New pos: (%lx.%04lx,%lx.%04lx)\n",
|
||||
(unsigned long)st->cursor.xpos >> 16,
|
||||
(unsigned long)st->cursor.xpos & 0xffff,
|
||||
(unsigned long)st->cursor.ypos >> 16,
|
||||
(unsigned long)st->cursor.ypos & 0xffff,
|
||||
(unsigned long)newx >> 16,
|
||||
(unsigned long)newx & 0xffff,
|
||||
(unsigned long)newy >> 16,
|
||||
(unsigned long)newy & 0xffff);
|
||||
#endif
|
||||
|
||||
/* Set the new cursor position */
|
||||
|
||||
st->cursor.xpos = newx;
|
||||
st->cursor.ypos = newy;
|
||||
|
||||
pos.x = b16toi(newx);
|
||||
pos.y = b16toi(newy);
|
||||
|
||||
printf("pwfb_move_cursor: Set position (%d,%d)\n", pos.x, pos.y);
|
||||
|
||||
ret = nxcursor_setposition(st->hnx, &pos);
|
||||
if (ret < 0)
|
||||
{
|
||||
printf("nxcursor_setposition: ERROR:"
|
||||
"nxcursor_setposition failed: %d\n",
|
||||
errno);
|
||||
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
/* Check for state changes */
|
||||
|
||||
switch (st->cursor.state)
|
||||
{
|
||||
case PFWB_CURSOR_MOVING:
|
||||
if (--st->cursor.countdown <= 0)
|
||||
{
|
||||
/* Set up for the the STATIONARY state next */
|
||||
|
||||
st->cursor.state = PFWB_CURSOR_STATIONARY;
|
||||
st->cursor.countdown = CURSOR_STATIONARY_DELAY;
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
case PFWB_CURSOR_STATIONARY:
|
||||
if (--st->cursor.countdown <= 0)
|
||||
{
|
||||
/* Set up for the the BLINKING state next */
|
||||
|
||||
st->cursor.state = PFWB_CURSOR_BLINKING;
|
||||
st->cursor.countdown = CURSOR_BLINKING_DELAY;
|
||||
st->cursor.blinktime = CURSOR_BLINK_DELAY;
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
case PFWB_CURSOR_BLINKING:
|
||||
if (--st->cursor.countdown <= 0)
|
||||
{
|
||||
/* Set up for the the MOVING state next */
|
||||
|
||||
st->cursor.state = PFWB_CURSOR_MOVING;
|
||||
st->cursor.countdown = CURSOR_MOVING_DELAY;
|
||||
st->cursor.visible = true;
|
||||
nxcursor_enable(st->hnx, true);
|
||||
}
|
||||
else if (--st->cursor.blinktime <= 0)
|
||||
{
|
||||
/* Toggle visibility */
|
||||
|
||||
st->cursor.blinktime = CURSOR_BLINK_DELAY;
|
||||
st->cursor.visible = !st->cursor.visible;
|
||||
nxcursor_enable(st->hnx, st->cursor.visible);
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
#endif
|
||||
|
||||
/****************************************************************************
|
||||
* Public Functions
|
||||
****************************************************************************/
|
||||
@ -198,5 +348,14 @@ bool pwfb_motion(FAR struct pwfb_state_s *st)
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef CONFIG_NX_SWCURSOR
|
||||
/* Move the cursor */
|
||||
|
||||
if (!pwfb_move_cursor(st))
|
||||
{
|
||||
printf("pwfb_motion: ERROR: pwfb_move_cursor failed\n");
|
||||
}
|
||||
#endif
|
||||
|
||||
return true;
|
||||
}
|
||||
|
@ -386,4 +386,3 @@ namespace NXWidgets
|
||||
#endif // __cplusplus
|
||||
|
||||
#endif // __APPS_INCLUDE_GRAPHICS_NXWIDGETS_CNXTKWINDOW_HXX
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user