WM MOTION - Swipe in window (Sample)

From SEGGER Wiki
Jump to: navigation, search
WM_MOTION_SwipeInWindow.c
Child window being swiped in.
File(s) required
  • WM_MOTION_SwipeInWindow.c
Runs in simulation Yes
Runs on target Yes
Download WM_MOTION_SwipeInWindow.c

This example demonstrates how a swipe in or swipe out gesture can be processed with motion support of the window manager. In this example upon the gesture an animation is started that moves a child window in or out.

Demo

Code

/*********************************************************************
*                    SEGGER Microcontroller GmbH                     *
*        Solutions for real time microcontroller applications        *
**********************************************************************
*                                                                    *
*        (c) 1996 - 2022  SEGGER Microcontroller GmbH                *
*                                                                    *
*        Internet: www.segger.com    Support:  support@segger.com    *
*                                                                    *
**********************************************************************

** emWin V6.26 - Graphical user interface for embedded applications **
emWin is protected by international copyright laws.   Knowledge of the
source code may not be used to write a similar product.  This file may
only  be used  in accordance  with  a license  and should  not be  re-
distributed in any way. We appreciate your understanding and fairness.
----------------------------------------------------------------------
File        : WM_MOTION_SwipeInWindow.c
Purpose     : Sample that demonstrates how motion input can be used
              to swipe in and out a window with a typical swipe gesture.
              After the swipe gesture is recognized, the window is moved
              with an animation.
Requirements: WindowManager - (x)
              MemoryDevices - ( )
              AntiAliasing  - ( )
              VNC-Server    - ( )
              PNG-Library   - ( )
              TrueTypeFonts - ( )
Wiki link   : https://wiki.segger.com/WM_MOTION_-_Swipe_in_window_%28Sample%29
---------------------------END-OF-HEADER------------------------------
*/

#include "DIALOG.h"

/*********************************************************************
*
*       Types
*
**********************************************************************
*/
typedef struct {
  int xPos;
  int yPosStart;
  int yPosEnd;
} ANIM_DATA;

/*********************************************************************
*
*       Defines
*
**********************************************************************
*/
#define CHILD_WIN_XSIZE        400
#define CHILD_WIN_YSIZE        60
#define CHILD_WIN_POS_MIN_Y    (-CHILD_WIN_YSIZE)
#define CHILD_WIN_POS_MAX_Y    20
#define MOVE_ANIM_PERIOD       250
#define UPPER_LIMIT_Y          60

/*********************************************************************
*
*       Static data
*
**********************************************************************
*/
static GUI_ANIM_HANDLE _hAnim;
static WM_HWIN         _hChildWin;

/*********************************************************************
*
*       Static code
*
**********************************************************************
*/
/*********************************************************************
*
*       _OnDelete
*/
static void _OnDelete(void * pVoid) {
  _hAnim = 0;
}

/*********************************************************************
*
*       _AnimWin
*/
static void _AnimWin(GUI_ANIM_INFO * pInfo, void * pVoid) {
  ANIM_DATA * pData;
  int         yNew;

  //
  // Calculate new position and move the child window.
  //
  pData = (ANIM_DATA *)pVoid;
  yNew  = pData->yPosStart + ((pData->yPosEnd - pData->yPosStart) * pInfo->Pos) / GUI_ANIM_RANGE;
  WM_MoveTo(_hChildWin, pData->xPos, yNew);
}

/*********************************************************************
*
*       _StartAnim
*/
static void _StartAnim(I8 Dir) {
  static ANIM_DATA Data;
  int              y;

  Data.xPos      = WM_GetWindowOrgX(_hChildWin);
  Data.yPosStart = (Dir > 0) ? CHILD_WIN_POS_MIN_Y : CHILD_WIN_POS_MAX_Y;
  Data.yPosEnd   = (Dir > 0) ? CHILD_WIN_POS_MAX_Y : CHILD_WIN_POS_MIN_Y;
  //
  // Only start animation if the new position is different from the current position.
  //
  y = WM_GetWindowOrgY(_hChildWin);
  if (Data.yPosEnd != y) {
    _hAnim = GUI_ANIM_Create(MOVE_ANIM_PERIOD, 25, (void *)&Data, NULL);
    GUI_ANIM_AddItem(_hAnim, 0, MOVE_ANIM_PERIOD, ANIM_ACCELDECEL, (void *)&Data, _AnimWin);
    GUI_ANIM_StartEx(_hAnim, 1, _OnDelete);
  }
}

/*********************************************************************
*
*       _OnMotion
*/
static void _OnMotion(WM_MESSAGE * pMsg) {
  WM_MOTION_INFO * pInfo;

  //
  // Motion input is handled the same for child and parent window.
  //
  pInfo = (WM_MOTION_INFO *)pMsg->Data.p;
  switch (pInfo->Cmd) {
  case WM_MOTION_INIT:
    pInfo->Flags |= (WM_MOTION_MANAGE_BY_WINDOW | WM_CF_MOTION_Y);
    break;
  case WM_MOTION_MOVE:
    //
    // Start animation if it is not currently running.
    //
    if (_hAnim == 0 && pInfo->dy) {
      //
      // Optional: when we swipe down, we only want to register swiping in the upper area of
      // the window (e.g. upper 60px).
      //
      if (pInfo->pState && (pInfo->dy > 0) && (pInfo->pState->y < UPPER_LIMIT_Y)) {
        _StartAnim(1);
      }
      //
      // For swiping up, we do not check the touch position.
      //
      else if (pInfo->dy < 0) {
        _StartAnim(-1);
      }
    }
    break;
  }
}

/*********************************************************************
*
*       _cbChildWin
*/
static void _cbChildWin(WM_MESSAGE * pMsg) {
  GUI_RECT Rect;

  switch (pMsg->MsgId) {
  case WM_PAINT:
    GUI_SetBkColor(GUI_BLUE);
    GUI_Clear();
    //
    // Display some text
    //
    WM_GetClientRect(&Rect);
    GUI_SetFont(&GUI_Font16_1);
    GUI_SetColor(GUI_WHITE);
    GUI_SetTextMode(GUI_TM_TRANS);
    GUI_DispStringInRect("Swipe up to move out this window...", &Rect, GUI_ALIGN_CENTER);
    break;
  case WM_MOTION:
    //
    // Send any motion messages to the parent window, since the gesture
    // should be processed the same.
    //
    _OnMotion(pMsg);
    break;
  default:
    WM_DefaultProc(pMsg);
    break;
  }
}

/*********************************************************************
*
*       _cbMainWin
*/
static void _cbMainWin(WM_MESSAGE * pMsg) {
  GUI_RECT Rect;

  switch (pMsg->MsgId) {
  case WM_CREATE:
    //
    // Create child window.
    //
    _hChildWin = WM_CreateWindowAsChild((LCD_GetXSize() / 2) - (CHILD_WIN_XSIZE / 2), -CHILD_WIN_YSIZE,
                                        CHILD_WIN_XSIZE, CHILD_WIN_YSIZE, pMsg->hWin, WM_CF_SHOW, _cbChildWin, 0);
    break;
  case WM_PAINT:
    GUI_SetBkColor(GUI_RED);
    GUI_Clear();
    //
    // Mark upper area of window.
    // This area will be where the swipe gesture will be accepted.
    //
    WM_GetClientRect(&Rect);
    GUI_SetColor(GUI_DARKRED);
    Rect.y1 = UPPER_LIMIT_Y - 1;
    GUI_FillRectEx(&Rect);
    //
    // Display text
    //
    GUI_SetFont(&GUI_Font16_1);
    GUI_SetTextMode(GUI_TM_TRANS);
    GUI_SetColor(GUI_WHITE);
    GUI_DispStringInRect("Swipe down in this darkred area...", &Rect, GUI_ALIGN_CENTER);
    break;
  case WM_MOTION:
    _OnMotion(pMsg);
    break;
  default:
    WM_DefaultProc(pMsg);
    break;
  }
}

/*********************************************************************
*
*       Public code
*
**********************************************************************
*/
/*********************************************************************
*
*       MainTask
*/
void MainTask(void) {
  GUI_Init();
  WM_MULTIBUF_Enable(1);
  WM_MOTION_Enable(1);
  //
  // Create main window.
  //
  WM_CreateWindowAsChild(0, 0, LCD_GetXSize(), LCD_GetYSize(), WM_HBKWIN, WM_CF_SHOW, _cbMainWin, 0);

  while (1) {
    GUI_Delay(100);
  }
}

/*************************** End of file ****************************/