479 lines
14 KiB
C
479 lines
14 KiB
C
#include "mywin_inc.h"
|
||
|
||
WIN_TouchWinStruct *WIN_CreatTouch(
|
||
WIN_WindowStruct *base,
|
||
void (*msgLoop)(struct _WIN_WindowStruct *win, WIN_MsgStruct *msg), int x,
|
||
int y, int x_size, int y_size) {
|
||
// 重设消息循环
|
||
void (*userMsgLoop)(struct _WIN_WindowStruct *win, WIN_MsgStruct *msg) = 0;
|
||
if (msgLoop == 0) {
|
||
msgLoop = (void (*)(struct _WIN_WindowStruct *win,
|
||
WIN_MsgStruct *msg))TOUCHWIN_DefaultMsgLoop;
|
||
} else {
|
||
userMsgLoop = msgLoop;
|
||
msgLoop = (void (*)(struct _WIN_WindowStruct *win,
|
||
WIN_MsgStruct *msg))TOUCHWIN_DefaultMsgLoop;
|
||
}
|
||
|
||
WIN_TouchWinStruct *ret = mymalloc(sizeof(WIN_TouchWinStruct));
|
||
// 调用父类的构造函数
|
||
if (ret) {
|
||
mymemset(ret, 0, sizeof(WIN_TouchWinStruct));
|
||
if (0 == WIN_CreatWindowExt((WIN_WindowStruct *)ret, base, msgLoop, x, y,
|
||
x_size, y_size)) {
|
||
// 创建失败
|
||
myfree(ret);
|
||
ret = 0;
|
||
} else {
|
||
// 构造一个
|
||
((WIN_WindowStruct *)ret)->winType = "WIN_TouchWinStruct";
|
||
((WIN_WindowStruct *)ret)->bkcolor = 0x342f2a;
|
||
((WIN_WindowStruct *)ret)->color = 0xc2ae9b;
|
||
((WIN_WindowStruct *)ret)->keyChid = 0; // 不作为子窗口被创建
|
||
ret->msgloop = (void (*)(struct _WIN_TouchWinStruct *win,
|
||
WIN_MsgStruct *msg))userMsgLoop;
|
||
}
|
||
}
|
||
|
||
return ret;
|
||
}
|
||
|
||
int WIN_CreatTouchEx(WIN_TouchWinStruct *win, WIN_WindowStruct *base,
|
||
void (*msgLoop)(struct _WIN_WindowStruct *win,
|
||
WIN_MsgStruct *msg),
|
||
int x, int y, int x_size, int y_size) {
|
||
// 重设消息循环
|
||
void (*userMsgLoop)(struct _WIN_WindowStruct *win, WIN_MsgStruct *msg) = 0;
|
||
if (msgLoop == 0) {
|
||
msgLoop = (void (*)(struct _WIN_WindowStruct *win,
|
||
WIN_MsgStruct *msg))TOUCHWIN_DefaultMsgLoop;
|
||
} else {
|
||
userMsgLoop = msgLoop;
|
||
msgLoop = (void (*)(struct _WIN_WindowStruct *win,
|
||
WIN_MsgStruct *msg))TOUCHWIN_DefaultMsgLoop;
|
||
}
|
||
|
||
// 调用父类的构造函数
|
||
if (win) {
|
||
mymemset(win, 0, sizeof(WIN_TouchWinStruct));
|
||
if (0 == WIN_CreatWindowExt((WIN_WindowStruct *)win, base, msgLoop, x, y,
|
||
x_size, y_size)) {
|
||
return 0;
|
||
} else {
|
||
// 构造一个
|
||
((WIN_WindowStruct *)win)->winType = "WIN_TouchWinStruct";
|
||
((WIN_WindowStruct *)win)->bkcolor = 0x342f2a;
|
||
((WIN_WindowStruct *)win)->color = 0xc2ae9b;
|
||
((WIN_WindowStruct *)win)->keyChid = 0; // 不作为子窗口被创建
|
||
win->msgloop = (void (*)(struct _WIN_TouchWinStruct *win,
|
||
WIN_MsgStruct *msg))userMsgLoop;
|
||
|
||
TOUCHWIN_SetOutCon(win, TOUCH_CON_RIGHT_PAR(x_size, y_size, 0));
|
||
|
||
return 1;
|
||
}
|
||
}
|
||
|
||
return 0;
|
||
}
|
||
|
||
// 创建子窗口函数
|
||
WIN_TouchWinStruct *WIN_CreatTouchChild(WIN_TouchWinStruct *base) {
|
||
WIN_WindowStruct *w_base = (WIN_WindowStruct *)base;
|
||
WIN_TouchWinStruct *ret =
|
||
WIN_CreatTouch(w_base, 0, 0, 0, w_base->x_size, w_base->y_size);
|
||
WIN_SetBackPic((WIN_WindowStruct *)ret);
|
||
|
||
mymemcpy(&ret->out, TOUCH_CON_UP_PAR(w_base->x_size, w_base->y_size, 0),
|
||
sizeof(TouchConditionStruct));
|
||
return ret;
|
||
}
|
||
|
||
// 创建父窗口函数
|
||
WIN_TouchWinStruct *WIN_CreatTouchBase(WIN_WindowStruct *base) {
|
||
WIN_WindowStruct *w_base = (WIN_WindowStruct *)base;
|
||
WIN_TouchWinStruct *ret =
|
||
WIN_CreatTouch(w_base, 0, 0, 0, w_base->x_size, w_base->y_size);
|
||
WIN_SetBackPic((WIN_WindowStruct *)ret);
|
||
return ret;
|
||
}
|
||
|
||
// 添加滑动时自动创建的子窗口
|
||
int TOUCHWIN_AddChild(WIN_TouchWinStruct *touch, TouchConditionStruct *c) {
|
||
if (touch->child_num < TOUCHWIN_CHILD_MAX_NUM) {
|
||
TouchConditionStruct *d = &touch->child[touch->child_num];
|
||
mymemcpy(d, c, sizeof(TouchConditionStruct));
|
||
touch->child_num++;
|
||
return 1;
|
||
}
|
||
return 0;
|
||
}
|
||
|
||
// 清空自动创建的子窗口
|
||
int TOUCHWIN_ClearChild(WIN_TouchWinStruct *touch) {
|
||
for (int i = 0; i < touch->child_num; i++) {
|
||
TouchConditionStruct *d = &touch->child[i];
|
||
mymemset(d, 0, sizeof(TouchConditionStruct));
|
||
}
|
||
touch->child_num = 0;
|
||
return 1;
|
||
}
|
||
|
||
// 设置退出动画
|
||
int TOUCHWIN_SetOutCon(WIN_TouchWinStruct *touch, TouchConditionStruct *c) {
|
||
c->creat = 0;
|
||
mymemcpy(&touch->out, c, sizeof(TouchConditionStruct));
|
||
return 1;
|
||
}
|
||
|
||
void TOUCHWIN_DefaultPaint(WIN_TouchWinStruct *touch) {
|
||
WIN_PaintBackGround((WIN_WindowStruct *)touch);
|
||
}
|
||
|
||
// 创建子窗口
|
||
int TOUCHWIN_CreatChild(WIN_TouchWinStruct *touch, WIN_MoveStruct *m) {
|
||
if (touch->work)
|
||
return 1;
|
||
|
||
for (int i = 0; i < touch->child_num; i++) {
|
||
RECT_Struct *rect = &touch->child[i].start;
|
||
if (POS_InRect(rect->x, rect->y, rect->x_size, rect->y_size, m->x_move,
|
||
m->y_move) == 1) {
|
||
if (touch->child[i].creat) {
|
||
touch->work = touch->child[i].creat(touch);
|
||
mymemcpy(&touch->work_con, &touch->child[i],
|
||
sizeof(TouchConditionStruct));
|
||
WIN_WindowStruct *win = (WIN_WindowStruct *)touch->work;
|
||
win->keyShield = 1; // 屏蔽按键
|
||
win->intercept = 0; // 不拦截发给父窗口的按键
|
||
if (touch->child[i].slide == TOUCH_SLIDE_DOWN) {
|
||
// 像下滑
|
||
WIN_Move((WIN_WindowStruct *)touch->work, 0,
|
||
-((WIN_WindowStruct *)touch)->y_size);
|
||
} else if (touch->child[i].slide == TOUCH_SLIDE_UP) {
|
||
// 像上滑
|
||
WIN_Move((WIN_WindowStruct *)touch->work, 0,
|
||
((WIN_WindowStruct *)touch)->y_size);
|
||
} else if (touch->child[i].slide == TOUCH_SLIDE_LEFT) {
|
||
// 像左滑
|
||
WIN_Move((WIN_WindowStruct *)touch->work,
|
||
((WIN_WindowStruct *)touch)->x_size, 0);
|
||
} else if (touch->child[i].slide == TOUCH_SLIDE_RIGHT) {
|
||
// 像右滑
|
||
WIN_Move((WIN_WindowStruct *)touch->work,
|
||
-((WIN_WindowStruct *)touch)->x_size, 0);
|
||
}
|
||
((WIN_WindowStruct *)touch->work)->keyShield = 1; // 不接受交互
|
||
}
|
||
return 1;
|
||
}
|
||
}
|
||
return 0;
|
||
}
|
||
|
||
// 移动子窗口
|
||
void TOUCHWIN_MoveChild(WIN_TouchWinStruct *touch, WIN_MoveStruct *m) {
|
||
int mov_x = m->x_move;
|
||
int mov_y = m->y_move;
|
||
WIN_WindowStruct *win = (WIN_WindowStruct *)touch->work;
|
||
|
||
int y = win->y + mov_y;
|
||
int x = win->x + mov_x;
|
||
TouchConditionStruct *child = &touch->work_con;
|
||
if (child->slide == TOUCH_SLIDE_DOWN) {
|
||
// child->creat 不为0则是进入动作
|
||
if (child->creat) {
|
||
if (y > 0)
|
||
y = 0;
|
||
} else {
|
||
if (y < 0)
|
||
y = 0;
|
||
}
|
||
WIN_SetPos(win, 0, y);
|
||
} else if (child->slide == TOUCH_SLIDE_UP) {
|
||
if (child->creat) {
|
||
if (y < 0)
|
||
y = 0;
|
||
} else {
|
||
if (y > 0)
|
||
y = 0;
|
||
}
|
||
WIN_SetPos(win, 0, y);
|
||
} else if (child->slide == TOUCH_SLIDE_LEFT) {
|
||
if (child->creat) {
|
||
if (x < 0)
|
||
x = 0;
|
||
} else {
|
||
if (x > 0)
|
||
x = 0;
|
||
}
|
||
WIN_SetPos(win, x, 0);
|
||
} else if (child->slide == TOUCH_SLIDE_RIGHT) {
|
||
if (child->creat) {
|
||
if (x > 0)
|
||
x = 0;
|
||
} else {
|
||
if (x < 0)
|
||
x = 0;
|
||
}
|
||
WIN_SetPos(win, x, 0);
|
||
}
|
||
}
|
||
|
||
// 在子窗口过程中触屏松开
|
||
void TOUCHWIN_ReleseChild(WIN_TouchWinStruct *touch, WIN_MoveStruct *m) {
|
||
int mov_x = m->x_move;
|
||
int mov_y = m->y_move;
|
||
WIN_WindowStruct *win = (WIN_WindowStruct *)touch->work;
|
||
WIN_WindowStruct *base = (WIN_WindowStruct *)touch;
|
||
TouchConditionStruct *child = &touch->work_con;
|
||
|
||
int xs = win->x;
|
||
int ys = win->y;
|
||
int xe = win->x + win->x_size - 1;
|
||
int ye = win->y + win->y_size - 1;
|
||
|
||
int ok = 0; // 此项为1,则创建定时器
|
||
|
||
// win->keyShield=0; //不屏蔽按键
|
||
// win->intercept=1; //拦截发给父窗口的按键
|
||
if (child->slide == TOUCH_SLIDE_DOWN) {
|
||
if (ye < child->dis) {
|
||
win->deleteWindow(win);
|
||
touch->work = 0;
|
||
} else
|
||
ok = 1;
|
||
} else if (child->slide == TOUCH_SLIDE_UP) {
|
||
if (base->y_size - ys < child->dis) {
|
||
win->deleteWindow(win);
|
||
touch->work = 0;
|
||
} else
|
||
ok = 1;
|
||
} else if (child->slide == TOUCH_SLIDE_LEFT) {
|
||
if (base->x_size - xs < child->dis) {
|
||
win->deleteWindow(win);
|
||
touch->work = 0;
|
||
} else
|
||
ok = 1;
|
||
} else if (child->slide == TOUCH_SLIDE_RIGHT) {
|
||
if (xe < child->dis) {
|
||
win->deleteWindow(win);
|
||
touch->work = 0;
|
||
} else
|
||
ok = 1;
|
||
}
|
||
|
||
if (ok) {
|
||
touch->timer_id = WIN_CreatTimer((WIN_WindowStruct *)touch, 20);
|
||
}
|
||
}
|
||
|
||
// 子窗口定时器处理
|
||
void TOUCHWIN_TimerChild(WIN_TouchWinStruct *touch) {
|
||
WIN_WindowStruct *win = (WIN_WindowStruct *)touch->work;
|
||
int x = win->x / 3;
|
||
int y = win->y / 3;
|
||
WIN_SetPos(win, x, y);
|
||
if ((y == 0) && (x == 0)) {
|
||
WIN_DeleteTimer(touch->timer_id);
|
||
touch->timer_id = 0;
|
||
win->keyShield = 0;
|
||
win->intercept = 1;
|
||
touch->work = 0;
|
||
}
|
||
}
|
||
|
||
// 判断滑动距离是否达到保留条件
|
||
static int check_slide_ok(WIN_TouchWinStruct *touch, TouchConditionStruct *t) {
|
||
WIN_WindowStruct *win = (WIN_WindowStruct *)touch;
|
||
if (t->slide == TOUCH_SLIDE_LEFT) {
|
||
if (t->creat) {
|
||
if (win->x_size - win->x > t->dis)
|
||
return 1;
|
||
} else {
|
||
if (-win->x < t->dis)
|
||
return 1;
|
||
}
|
||
} else if (t->slide == TOUCH_SLIDE_RIGHT) {
|
||
if (t->creat) {
|
||
if (win->x + win->x_size > t->dis)
|
||
return 1;
|
||
} else {
|
||
if (win->x < t->dis)
|
||
return 1;
|
||
}
|
||
} else if (t->slide == TOUCH_SLIDE_UP) {
|
||
if (t->creat) {
|
||
if (win->y_size - win->y > t->dis)
|
||
return 1;
|
||
} else {
|
||
if (-win->y < t->dis)
|
||
return 1;
|
||
}
|
||
} else if (t->slide == TOUCH_SLIDE_DOWN) {
|
||
if (t->creat) {
|
||
if (win->y + win->y_size > t->dis)
|
||
return 1;
|
||
} else {
|
||
if (win->y < t->dis)
|
||
return 1;
|
||
}
|
||
}
|
||
return 0;
|
||
}
|
||
|
||
// 处理子窗口消息,有返回1,无返回0
|
||
int TOUCHWIN_ChildMsg(WIN_TouchWinStruct *touch, WIN_MsgStruct *msg) {
|
||
int ret = 0;
|
||
switch (msg->data.v) {
|
||
case TOUCH_CHILD_MOV_START:
|
||
touch->work = (WIN_TouchWinStruct *)msg->data2.v;
|
||
mymemcpy(&touch->work_con, &touch->work->out, sizeof(TouchConditionStruct));
|
||
ret = 1;
|
||
break;
|
||
case TOUCH_CHILD_MOV_END:
|
||
if ((u32)touch->work == msg->data2.v) {
|
||
WIN_WindowStruct *win = (WIN_WindowStruct *)touch->work;
|
||
if (check_slide_ok(touch->work, &touch->work_con) == 0) {
|
||
win->deleteWindow(win);
|
||
touch->work = 0;
|
||
} else {
|
||
touch->timer_id = WIN_CreatTimer((WIN_WindowStruct *)touch, 20);
|
||
}
|
||
ret = 1;
|
||
}
|
||
|
||
break;
|
||
default:
|
||
break;
|
||
}
|
||
return ret;
|
||
}
|
||
|
||
// 惯性定时器消息
|
||
int TOUCHWIN_TimerInertia(WIN_TouchWinStruct *touch) {
|
||
if (touch->x_inertia > 0)
|
||
touch->x_inertia--;
|
||
else if (touch->x_inertia < 0)
|
||
touch->x_inertia++;
|
||
if (touch->y_inertia > 0)
|
||
touch->y_inertia--;
|
||
else if (touch->y_inertia < 0)
|
||
touch->y_inertia++;
|
||
|
||
// 惯性滑动
|
||
WIN_SendTouchMove((WIN_WindowStruct *)touch, touch->x_inertia,
|
||
touch->y_inertia);
|
||
|
||
if (touch->y_inertia == 0 && touch->x_inertia == 0) {
|
||
WIN_DeleteTimer(touch->timer_inertia);
|
||
touch->timer_inertia = 0;
|
||
}
|
||
return 0;
|
||
}
|
||
|
||
// 默认消息循环
|
||
void TOUCHWIN_DefaultMsgLoop(WIN_TouchWinStruct *touch, WIN_MsgStruct *msg) {
|
||
WIN_MoveStruct *m = 0;
|
||
WIN_KeyStruct *k = 0;
|
||
int ok = 1; // 此项为1,则调用用户消息处理函数
|
||
switch (msg->msg) {
|
||
// case WIN_MSG_PAINT:
|
||
// TOUCHWIN_DefaultPaint(touch);
|
||
// break;
|
||
case WIN_MSG_MOVE:
|
||
m = msg->data.p;
|
||
switch (m->moveType) {
|
||
case MOVE_DATA_TOUCHIN:
|
||
case MOVE_DATA_MOVEIN: {
|
||
// 清除惯性定时器
|
||
if (touch->timer_inertia) {
|
||
WIN_DeleteTimer(touch->timer_inertia);
|
||
touch->timer_inertia = 0;
|
||
touch->x_inertia = 0;
|
||
touch->y_inertia = 0;
|
||
}
|
||
|
||
RECT_Struct *rect = &touch->out.start;
|
||
if (POS_InRect(rect->x, rect->y, rect->x_size, rect->y_size, m->x_move,
|
||
m->y_move) == 1) {
|
||
// 触发了退出动作
|
||
touch->move_start = 1;
|
||
((WIN_WindowStruct *)touch)->intercept = 0;
|
||
WIN_SetChildWinkeyShield((WIN_WindowStruct *)touch, 1);
|
||
WIN_SendMsgToPrent((WIN_WindowStruct *)touch, TOUCH_CHILD_MOV_START,
|
||
(u32)touch);
|
||
ok = 0;
|
||
} else if (TOUCHWIN_CreatChild(touch, m) == 1) {
|
||
ok = 0;
|
||
}
|
||
} break;
|
||
case MOVE_DATA_MOVED:
|
||
if (touch->work) {
|
||
TOUCHWIN_MoveChild(touch, m);
|
||
ok = 0;
|
||
} else if (touch->move_start) {
|
||
ok = 0;
|
||
} else if (touch->timer_inertia == 0) {
|
||
// 存储惯性值
|
||
touch->x_inertia = m->x_move;
|
||
touch->y_inertia = m->y_move;
|
||
}
|
||
break;
|
||
case MOVE_DATA_TOUCHOUT:
|
||
case MOVE_DATA_MOVEOUT:
|
||
if (touch->work) {
|
||
TOUCHWIN_ReleseChild(touch, m);
|
||
ok = 0;
|
||
} else if (touch->move_start) {
|
||
touch->move_start = 0;
|
||
((WIN_WindowStruct *)touch)->intercept = 1;
|
||
WIN_SetChildWinkeyShield((WIN_WindowStruct *)touch, 0);
|
||
WIN_SendMsgToPrent((WIN_WindowStruct *)touch, TOUCH_CHILD_MOV_END,
|
||
(u32)touch);
|
||
ok = 0;
|
||
} else {
|
||
// 添加惯性定时器
|
||
if ((touch->timer_inertia == 0) &&
|
||
(touch->x_inertia || touch->y_inertia))
|
||
touch->timer_inertia = WIN_CreatTimer((WIN_WindowStruct *)touch, 20);
|
||
else if (touch->timer_inertia == 0) {
|
||
// 滑动停止
|
||
WIN_SendTouchMove((WIN_WindowStruct *)touch, 0, 0);
|
||
}
|
||
}
|
||
break;
|
||
// if(touch->work)
|
||
// {
|
||
// TOUCHWIN_ReleseChild(touch,m);
|
||
// ok=0;
|
||
// }
|
||
// break;
|
||
default:
|
||
break;
|
||
}
|
||
break;
|
||
case WIN_MSG_TIMER:
|
||
if (msg->data.v == touch->timer_id) {
|
||
TOUCHWIN_TimerChild(touch);
|
||
ok = 0;
|
||
} else if (msg->data.v == touch->timer_inertia) {
|
||
TOUCHWIN_TimerInertia(touch);
|
||
ok = 0;
|
||
}
|
||
break;
|
||
case WIN_MSG_CHID:
|
||
if (TOUCHWIN_ChildMsg(touch, msg) == 1) {
|
||
ok = 0;
|
||
}
|
||
break;
|
||
default:
|
||
WIN_DefaultMsgLoop((WIN_WindowStruct *)touch, msg);
|
||
break;
|
||
}
|
||
|
||
// 调用用户消息处理函数
|
||
if (ok && touch->msgloop)
|
||
touch->msgloop(touch, msg);
|
||
}
|